Let’s Play VimGolf

Or VimGolf in Emacs anyway. Over at Life seen through a coder’s eyes, Yassine Chaouche poses the following problem. Starting with an Emacs buffer containing only

[[Image(grep_1.png)]]

end up with

[[Image(grep_1.png)]]
[[Image(grep_2.png)]]
[[Image(grep_3.png)]]
[[Image(grep_4.png)]]
[[Image(grep_5.png)]]
[[Image(grep_6.png)]]
[[Image(grep_7.png)]]
[[Image(grep_8.png)]]

Chaouche solves this problem using CUA mode. If you use CUA mode, you should take a look at his solution; you may find it will serve as a template for similar problems you may encounter.

I’ve never used CUA mode in Emacs or, before I saw the light, Vim so his solution doesn’t work for me. It also seems as if it uses more keystrokes than necessary. (This is VimGolf in Emacs, remember.) To me, this cries out for a macro. Here’s what I did

Keystrokes Action Buffer
<start state> ▮[[Image(grep_1.png)]‍]
Ctrl+k kill line
Ctrl+1 F3 set macro counter to 1
and begin macro
Ctrl+y yank line [[Image(grep_1.png)]‍]▮
Ctrl+r 1 search backwards for 1 [[Image(grep_▮1.png)]‍]
Ctrl+d delete 1 [[Image(grep_▮.png)]‍]
F3 insert macro counter [[Image(grep_1▮.png)]‍]
Ctrl+e end of line [[Image(grep_1.png)]‍]▮
Return new line [[Image(grep_1.png)]‍]
F4 end macro [[Image(grep_1.png)]‍]
Ctrl+7 F4 play macro 7 times <end state>

That’s a solution in just 13 keystrokes. The problem is simpler, but takes more keystrokes, if you start with an empty buffer. Then it’s just 【Ctrl+1 F3】 to set the macro counter and start recording, the text [‍[Image(grep_, 【F3】 to insert the counter, and finally the text .png)]] followed by 【Return F4】 to move to the next line and stop recording. Then 【Ctrl+7 F4】 inserts the other 7 lines as before.

This post really should have been a video but I’m not set up for that. Besides, I don’t have a cool voice like Magnar Sveen.

This entry was posted in General and tagged . Bookmark the permalink.

4 Responses to Let’s Play VimGolf

  1. Krister Svanlund says:

    To me this is a excellent example of when Vim actually is much smoother than emacs, both solutions (cua and this with macros) feels very clunky for me. In vim i just did qayypq6@a all of which are commands I use everyday when coding.

    qa – start recording to a
    yy – yank this line
    p – paste last line
    – increase number on line (i actually hacked together this command in emacs before i saw the light)
    q – stop recording
    6@a – repeat macro at a 6 times

    These are no mysterious F#-keys or character for character stepping, just plain old vim commands… infact it can be done without planning or moving your hand from the home-row… and it’s possible to insert any number of these rows just by adjusting one number in the action.

    The only thing that really bothers me with vim is that it doesn’t have any decent scripting language… that is where emacs really shines :)

    • Krister Svanlund says:

      Of course my <ctrl-a> was swallowed by the filtering system. qayyp<ctrl-a>q6@a is the correct command…

  2. Phil says:

    jcs: Note that you can reduce your keystrokes by one simply by leaving out that first F4

Leave a Reply

Your email address will not be published. Required fields are marked *

You may use these HTML tags and attributes: <a href="" title=""> <abbr title=""> <acronym title=""> <b> <blockquote cite=""> <cite> <code> <del datetime=""> <em> <i> <q cite=""> <strike> <strong>