Paragraphs
Blank lines are paragraph breaks: } and { jump to the next and previous one, and d} cuts a whole function from the break above it.
Thursday, 4:30 p.m. Turning pages in legacy.js all afternoon, you started to see its shape: every function is a block of lines with a blank line before and after. Constants together, then one function, a gap, the next function, a gap.
Paragraphs, in other words. And Vim reads code in paragraphs too.
Warm-up from earlier chapters
Two from earlier chapters, from memory, before the new idea. Two wrong tries show the answer.
Paragraph breaks
To Vim, a paragraph is a run of lines with something on them, and a blank line is the break between paragraphs. } jumps forward to the next break, and { jumps back to the previous one. In code that means one key from function to function, however long each one is.
function totalFor(order) { const base = subtotal(order.items); const tax = taxFor(base); const tip = order.tip || 0; return base + tax + tip;}// DEAD CODE: the fax ordering line was switched off in 2020function faxOrder(order) { const sheet = renderFaxSheet(order); faxMachine.send(sheet, "+1-555-0100"); log("fax sent", order.id); return true;}function totalFor(order) { const base = subtotal(order.items); const tax = taxFor(base); const tip = order.tip || 0; return base + tax + tip;}// DEAD CODE: the fax ordering line was switched off in 2020function faxOrder(order) { const sheet = renderFaxSheet(order); faxMachine.send(sheet, "+1-555-0100"); log("fax sent", order.id); return true;}function totalFor(order) { const base = subtotal(order.items); const tax = taxFor(base); const tip = order.tip || 0; return base + tax + tip;}// DEAD CODE: the fax ordering line was switched off in 2020function faxOrder(order) { const sheet = renderFaxSheet(order); faxMachine.send(sheet, "+1-555-0100"); log("fax sent", order.id); return true;}Hop the breaks
Targets sit on the first line of a function. } lands on the break before it, so it's } and then j; { for the ones behind you.
This exercise needs a keyboard. Read on, and play it at your computer.
Where does } stop?
The cursor is inside totalFor. You press }. Where does it land?
} is a noun
Every motion is a noun, and } is a big one: to the next break. From the blank line above a function, d} reads delete to the next break and takes the whole function, leaving a single blank line where it was. One sentence per dead function.
function totalFor(order) { const base = subtotal(order.items); const tax = taxFor(base); const tip = order.tip || 0; return base + tax + tip;}// DEAD CODE: the fax ordering line was switched off in 2020function faxOrder(order) { const sheet = renderFaxSheet(order); faxMachine.send(sheet, "+1-555-0100"); log("fax sent", order.id); return true;}function validateOrder(order) { if (!order.items || order.items.length === 0) return "empty"; if (order.items.some((i) => i.qty <= 0)) return "bad quantity"; if (!order.address) return "no address"; if (!isOpen(new Date())) return "closed"; return null;}function applyCoupon(order, code) { const coupon = COUPONS[code]; if (!coupon) return order; if (coupon.expires < Date.now()) return order; const off = Math.round(subtotal(order.items) * coupon.percent); return { ...order, discount: off };}function studentDiscount(order, user) { if (!user.isStudent) return 0; return Math.round(subtotal(order.items) * 0.1);}// DEAD CODE: loyalty points were replaced by the app in 2021function addLoyaltyPoints(user, order) { const points = Math.floor(totalFor(order) / 100); user.points = (user.points || 0) + points; saveUser(user); return points;}Two dead paragraphs
Two functions marked dead. Get onto the blank line above each one, then d}.
The first exercise of every lesson is free. Pro unlocks the rest, every track, for good.
See ProThis exercise needs a keyboard. Read on, and play it at your computer.
Is it a break?
Line 3 looks empty, but it holds four spaces. Line 6 is truly empty. From line 1 you press }. Where does the cursor land?
The gap that isn't
Same constants. Empty line 3 (the editor shows its four spaces as the part to delete), then check from the top that } stops there now.
The first exercise of every lesson is free. Pro unlocks the rest, every track, for good.
See ProThis exercise needs a keyboard. Read on, and play it at your computer.
A paragraph is layout, not a function
d} cuts to the next blank line, whatever the code means. In legacy.js every function happens to be one paragraph. If a function has a blank line inside it, that's a break too, and d} stops halfway through. Before you cut, press } on its own and see where the break is.
function taxFor(amount) { return Math.round(amount * TAX_RATE);}// DEAD CODE: the tip jar on the old kioskfunction tipJar(order) { const options = [1, 2, 3]; return options.map((n) => order.total + n * 100);}function totalFor(order) { const base = subtotal(order.items); return base + taxFor(base);}function taxFor(amount) { return Math.round(amount * TAX_RATE);}// DEAD CODE: the tip jar on the old kioskfunction tipJar(order) { const options = [1, 2, 3]; return options.map((n) => order.total + n * 100);}function totalFor(order) { const base = subtotal(order.items); return base + taxFor(base);}tipJar: d} stops at the blank line inside it; d2} reaches the break after it.Halfway through
A different file, the old kiosk code. Someone already pressed d} from the break above tipJar, and only half the function went. Undo it with u, then cut the whole function with a count: two breaks on.
The first exercise of every lesson is free. Pro unlocks the rest, every track, for good.
See ProThis exercise needs a keyboard. Read on, and play it at your computer.
Paragraphs, from memory
Press the keys.
Function hopping
Twelve function starts all over legacy.js. Breaks, counts, page numbers: whatever gets there first.
The first exercise of every lesson is free. Pro unlocks the rest, every track, for good.
See ProThis exercise needs a keyboard. Read on, and play it at your computer.
Three dead paragraphs
The first three dead functions in legacy.js, top to bottom: the fax line, the loyalty points and the pager. Cut each one out, comment and all, leaving one blank line between the functions around it. The other three can wait until tomorrow.
Stuck? Show a hint
The first exercise of every lesson is free. Pro unlocks the rest, every track, for good.
See ProThis exercise needs a keyboard. Read on, and play it at your computer.
Extra practice optional
The chapter is done. These rounds keep going as long as you like: stop whenever it stops being useful.
Paragraph hopping
Endless function starts across the file.
The first exercise of every lesson is free. Pro unlocks the rest, every track, for good.
See ProThis exercise needs a keyboard. Read on, and play it at your computer.