Skip to content

Fun with Vimgolf 3: Swapping Words by Sorting

Jan 14 13
by mickey

Jon over at Irreal’s been busy with VimGolf challenges, and I figured I’d throw in my two pieces of eight.

The “challenge” is a simple. Take this text:

And turn it into

As you can see, a simple transposition between two words on a line is all that we need, and Jon’s come up with a solution that solves it in 8 keystrokes. Arguably something like his solution is what I would do were I to do it in real life.

I’m not sure if the Vim guys count typing out strings of text as one atomic operation or if they count each character; in Emacs, arguably, each character is in itself a command as each key stroke will invoke self-insert-command but it’s more fun to think of strings of text as a single keystroke, for simplicity’s sake, and to give ourselves a sporting chance against our Vim nemeses.

So here’s my solution. It only solves this particular challenge and nothing more. It relies on the good ole sort order — that C come before S.

Command Description
C-x h Mark whole buffer
M-x sort-regexp-fields Run sort-regexp-fields. See Sorting Text by Line, Field and Regexp in Emacs for more information
Regexp specifying records to sort: \\([a-z_]+\\)$ We want each record -- that's the part of the line we want Emacs to use for sorting -- to be the last word on each line
Regexp specifying key within record: \\1 The key -- that's the part inside the capturing group from above -- we want to sort by is the entire capturing group.

And we're done. So how does it work? Well, we rely on the side effect that the word CHALLENGE_FOLDER is less than, lexicographically, SOLUTIONS_FOLDER, because C comes before S.

It boils down to this: sort-regexp-fields is pure magic. As my article on the subject talks about at length, you can tell Emacs to only sort by parts of a line -- the part that matches the regular expression -- and using that match, you can then tell Emacs how you want to sort that data. We tell Emacs to sort by the last word on each line and leave the rest untouched. Simple :)

So how many keystrokes is that? Good question. I don't know: it depends on how you count it. Two if you count the commands only; four if you count the commands and the prompts; and many more if you count each character.

As always, these challenges are pointless (though fun!) but they do force you to think on your feet.

Jedi: A completion library for Python

Jan 10 13
by mickey

If you’re using Python with Emacs (using one of several competing, incompatible, and slightly different modes) you are used to a pretty… bare-bones experience: no completion; semi-functional dynamic docstring support; and little in the way of two-way communication between Python and Emacs.

Enter Jedi, a completion library. Yes, Jedi, an editor-agnostic library that publishes auto completion, docstring support, and more. Excellent.

I’ve experimented with Pymacs — an interesting science project that adds “Python-like” support Emacs, so you can avoid interacting with Elisp, except not really — rope, and ropemacs and they were… disappointing. Slow, crash-prone, obtuse and impossible to extend. So I never really used them, and lived without completion or, well, much of anything beyond the REPL and my own handcrafted modifications.

The other alternative is the 600 lbs gorilla, CEDET, and its incomplete Python support, but that’s no good either.

Imagine my surprise, after fidgeting with the dependencies for both Jedi and Jedi.el, the Emacs library for Jedi, that it… works! And it’s good! It’s up-and-coming, I should say, but perfectly usable; it doesn’t get in my way, it’s got some crazy deferreds library it depends on for asynchronous, non-blocking querying of Jedi, but that bit works great — no input lag at all.

It seems to resolve, simplistically (which is good), as many assignments and method calls as one can reasonably expect from a non-evaluating, statically analyzing Python completion library.

Functioning Auto Complete in a Python buffer

The Jedi.el module also Just Works with the excellent auto-complete library, as you can see in the picture above.

Aside from completion, it also offers “find symbol definition at point” (a la TAGS, but not crap) and Jedi.el sensibly binds it to C-. by default. It also has a “related names” functionality, tracking down same-named identifiers in other modules; it uses Anything (now Helm) to display the results, and it is bound to C-c r. And finally, it can show the documentation for the identifier at point (be it a class or function) with C-c d. Useful.

I haven’t used Jedi and Jedi.el long enough to really get to know it, but I’m probably going to extend Jedi.el so it uses eldoc-mode for displaying the function parameters; it’s also a bit rough around the edges, and I may want to tweak certain things to my liking, but overall: huge success!

I highly recommend you give Jedi and Jedi.el a try!

IEdit: Interactive, multi-occurrence editing in your buffer

Oct 2 12
by mickey

Have you ever heard of iedit for Emacs by Victor Ren (Update:Seems the github link I posted earlier was way out of date)? Me neither, until recently, and that’s a terrible shame as it is a cornerstone of my programming workflow now that I’ve learned about it. So what does it do, then? Well, quite simply, you can edit multiple, identical string occurrences at the same time. The twist here is it uses in-buffer editing without disrupting your workflow with prompts, windows or any of that stuff: you plonk your point down on a word you want to change; you run iedit-mode; and now all the occurrences of that word is highlighted on your screen, like isearch, and when you alter a highlighted word, the other highlighted words change also. How cool is that? Modern IDEs have it already — usually hidden away in the “Refactoring” section — and does exactly the same thing, but iedit is a lot dumber as it cannot infer context beyond I want to iedit all occurrences of word point is on.

If you regularly replace variables or words with M-% or C-M-% — well, you can retire that workflow now, as iedit will handle it for you. Sure, go ahead; use the older way if you have complex, partial replacements you want to do, but if you’re renaming a variable in a buffer… Why not use iedit?

Here’s a sample demonstration showing what exactly it is I’m talking about, in brilliant technicolor:

Emacs with IEdit active

Improving iedit

So iedit’s pretty great and all that, but I don’t replace words across a whole buffer very often; sure, I hear you say: “just narrow-to-defun with C-x n d!” Indeed, narrowing’s great, but this blog is all about half-baked, half-inventions and cobbled-together scripts, and this post is no exception!

I prefer a workflow that minimizes the use of commands to do routine tasks — a fairly common goal for most Emacs hackers. The code below aim to do just that: when invoked, it will take the word at point and only iedit occurrences in the local defun (Note: don’t forget that although defun is Lisp-speak, most modes automatically support commands like mark-defun or narrow-to-defun.) If you pass an argument to the function, it will iedit all occurrences in the entire buffer.

The iedit author suggest that you bind iedit-mode — the default command for entering iedit — to C-; and I agree: it’s rarely used and easy to type.

Update: Le Wang pointed out that I was using an older version of iedit; the code has been updated to reflect the API changes.