2010-11-21
Why I think some coding tricks are especially damaging
Over time, I've come to the opinion that some programming tricks are more damaging to your code's readability than others. I think that there are at least two sorts of coding tricks, which I will call opaque tricks and impossible tricks, and impossible tricks are more damaging than opaque tricks.
An opaque trick is one where the reader stares at the code and has no idea what it does. Either they don't understand the operations, or they don't understand what the results of doing the operations are (perhaps you are playing odd bit tricks), or they can't follow the flow of control, or any number of other things that leave them lost. An impossible trick is one where you do something that ought to be impossible, except that clearly it works because your code runs; for example, in Python you use something from a module without explicitly importing it.
(Sometimes these categories overlap in actual code.)
The problem with impossible tricks is that they destroy the reader's confidence in their understanding of the code. Since something that you thought is impossible is happening anyways, clearly your understanding of the code to date is incorrect and you've missed something important while reading the code; you need to start over, more carefully and cautiously. In effect, an impossible trick damages or destroys the reader's confidence in everything they think that they know or have worked out about your code.
By contrast, opaque code is just a local issue. The reader knows that they don't understand this code and they're going to have to study it carefully (or trust the comments), but their understanding of other code is undamaged; their uncertainty is local instead of complete. Someone who is skimming can even skip working out how the code works and just assume that it does (which is fine as long as they don't need to change or debug it).
2010-11-16
When good ideas go bad: how not to do a file chooser dialog
I hate the modern Gnome file chooser dialog. Fortunately its problems make a great illustration of the perils of falling victim to a good idea.
The good idea that infected the modern Gnome file chooser dialog is showing a preview of the file you've selected (provided that it is a preview'able media type, such as a picture). This would be a great idea if it worked instantaneously, and perhaps it does on some people's machines. But on slow machines it is most of a usability disaster, because the implementation freezes the dialog while it generates the preview.
What this does is turn selecting an image file from a quick double-click into a sequence where you click, the dialog stalls as you click again, and a second later a postage stamp preview of the image flickers present for a moment before the entire dialog disappears (because you have, after all, selected a file). The implementation has turned a good idea into something that slows people down and damages system responsiveness.
The other usability problem with these previews is that they resize the file chooser dialog on the fly; when a preview is generated, the dialog expands to the right to accommodate it. This causes problems for dialog placement and is visually distracting, all for what is presumably supposed to be a bonus feature.
Unfortunately part of the problem here is the weakness of the traditional Unix library based programming model, which makes it quite hard to do asynchronous processing in a way that is sandboxed from other libraries and the rest of the application. This is especially so if you really need to be able to call other libraries that were in turn not necessarily written to be thread-safe and to carefully sandbox themselves, as the file chooser dialog may well need to in order to interpret various media formats.
Sidebar: how to do it right
In my opinion, the way to do this right is:
- preview generation should be asynchronous.
- the dialog should always have a space for the preview.
- when the preview is being generated, you can have a discreet, faded 'processing' animation of some sort occupying the space.
- if no preview can be generated, put a faded 'not available' icon in the space.
- once the preview is available, fade it in to the already-established space.
You want status information to be low-key because it is a low priority thing; you do not want it to distract people from the actual file list.
2010-11-15
The language dilemma for production software
Right now, I'm feeling enthused about the idea of writing some things in one of the interesting new languages and environments, such as Go or node.js. But here's where things collide with my problems with learning languages; if I'm going to write any significant amount of code in these new languages, it has to do something real. And most of the real things that I have to do are not personal projects but software that I would want to use in our environment here.
Which leads to my dilemma: how can I justify inflicting production software written in a peculiar language on my co-workers? I don't exactly want to gift them with a black-box program that's important to our systems, one that only I can possibly work on. Thus, if I'm going to use a new language for some piece of software I need to be able to make a reasonably convincing case that it provides some compelling benefit over writing the software in a language that my co-workers are already familiar with, and that I'm not just complicating my co-workers' lives because I like shiny new stuff.
Unfortunately, so far I haven't been able to come up with very compelling justifications, not even of the 'this is by far the most productive language for me to write this in' sort. Possibly this is because I don't know these languages well enough, but this is sort of a chicken and egg problem.
(At least not for Go or node.js; there is a killer feature that I could use in some language, but I don't think that either has it.)
As a side note, this means that languages being well supported in our Linux distributions is especially important, because I can just imagine my co-workers' faces if the instructions for maintaining one of my programs start with 'first, download the language source code and compile it'. Sadly, this is an area that neither Go nor node.js seem to be doing very well on at the moment.
A corollary to this is that the best sort of real programs for me to write in a new language are things that do essentially offline processing of data, such as log scanning and summarization. If I want to crunch weeks of mail logs to analyze delivery delays or spam levels, most of the time it doesn't matter what language I write it in because it doesn't matter if it breaks. (In fact such log analysis may only be done by hand once in a while in the first place.)
Sadly (you saw this one coming) I don't currently have any such work that needs anything more than awk, or maybe Python.
(Doing log analysis on our DNS query logs was my first use of the bstring library for C, precisely because I had enough data to go through that Python or awk didn't cut it any more.)
PS: to be utterly clear: I am not saying that production software shouldn't be written in new languages, or that it should only be written in new languages when they provide a compelling benefit.