Telephone +44(0)1524 64544

Buy Pizza. Pay with snakes ... Eat Bicycle.

TMTOWTDI but which one makes most sense?

Mon May 18 22:00:00 2009

Digg! submit to reddit Delicious RSS Feed Readers

Buy pizza. Pay with snakes ... Fsck pizza. Eat bicycle.

So, before I start explaining why the hell I chose this particular post title, I need to show you a piece of perl code:

BEFOREHAND: close door, each window & exit; wait until time.
    open spellbook, study, read (scan, select, tell us);
write it, print the hex while each watches,
    reverse its length, write again;
    kill spiders, pop them, chop, split, kill them.
        unlink arms, shift, wait & listen (listening, wait),
sort the flock (then, warn the "goats" & kill the "sheep");
    kill them, dump qualms, shift moralities,
    values aside, each one;
        die sheep! die to reverse the system
        you accept (reject, respect);
next step,
    kill the next sacrifice, each sacrifice,
    wait, redo ritual until "all the spirits are pleased";
    do it ("as they say").
do it(*everyone***must***participate***in***forbidden**s*e*x*).
return last victim; package body;
    exit crypt (time, times & "half a time") & close it,
    select (quickly) & warn your next victim;
AFTERWORDS: tell nobody.
    wait, wait until time;
    wait until next year, next decade;
        sleep, sleep, die yourself,
        die at last
# Larry Wall

Or at least, purportedly perl according to the wikipedia page I retrieved it from (which notes the author is unknown - if you are they and would prefer I not reproduce this, please tell me). It doesn't seem to -quite- compile here but I'm going to handwave that away on grounds of irrelevance.

Here's my point. Or at least the start of it: perl can (could?) parse code like that. Your brain quite happily parsed the title of this post before going "wtf? that makes no actual sense". There is a pattern here.

The annoying thing about natural language, especially IME english, is that it gives you a lot of rope. It's flexible, contextual and you can generally interpret even very odd looking sentences to some extent. Including the sort-of-a-sentence I used for a title. The fact it could almost be mistaken for a sentence (and that a computer doing only grammar recognition almost certainly would do so) doesn't make it good english. The advantage of having that much rope is that it buys us the opportunity to be expressive.

By expressive here I think I'm trying to mean "lets us express the letter of the thing in a way that also implies the spirit of the thing". So ... to my mind Modern Perl is aiming to express a pretty similar thing to Enlightened Perl in terms of the letter of it - modern, sensible practices in code. However, the former is merely a clinical description whereas the latter implies a sense of forward motion and association with a mindset, a fusion of art and science that moved the entire world forward. It tries to capture an understanding of why you should care, why you should want to be part of this, in a way that "modern" just doesn't.

Which brings us to: expressiveness is important. It allows you to show a lot more information than a clinical language can - try conveying emotional undercurrents in lojban, for example. So, in perl one can write -

  some_code($some,$args) or die "Some message";

  die "Some message" unless some_code($some,$args);

  unless (some_code($some,$args)) {
    die "Some message";

- and the code that each compiles into will be equivalent (and depending on how much the optimiser loves you today, quite possibly run-time identical).

However, all three -express- something different, at least to the skimming eye trying to get the shape of the thing before delving into the details. The first one makes the call to the routine most obvious, the second the exception and the third the structure of the conditional. Effectively, the choice of syntax to produce the given semantics is providing emphasis to the code in the eye of the reader.

So, for example, I'd tend to use the first one to express wanting an action to happen and incidentally needing to bail out if it goes wrong -

  open my $file, '', $filename
    or die "Error opening ${filename}: $!";

- and by putting the or onto a second line, emphasise its being a subsidiary clause that's not crucial to understanding of the overall purpose of the routine.

The second, on the other hand, is preferred for cases where the primary purpose it to throw a useful and clear exception if required and the test is merely there as part of that purpose -

  die "Don't have permission to read ${filename}"
    unless -r $filename;

For such simple cases, I almost certainly wouldn't use the block form - the point at which that becomes advantageous is where there's more complexity to the test and the additional syntactic structure becomes useful as a form of delineation. So, perhaps:

  unless (verify_file($file)) {
    close $file or die "Couldn't close filehandle to corrupt file ${filename}";
    unlink $file or die "Couldn't unlink corrupt file ${filename}";
    die "Failed to verify ${filename}, cleaned up";

Rewriting this into either of the other two forms would require either a block or some monstrosity like chained && calls or comma operator abuse - and this way the seeking eye can see the unless at the head of the block and know that this is the "exception to the rule" branch - and if that's not what they're currently looking for skip their eye to the end of the block via the indentation and bracing.

Linguistic expression can provide implicit semantic weighting to otherwise identical wording, and this is an important tool in the continuing fight to make programs that are easy for another human to come along and understand - the computer might not care what you mean so long as doing what you say produces the right answer, but to a maintenance programmer the purpose of a piece of code is often far more important to figure out than the detailed mechanics, and any tool we can provide to make it easier to do so can only be a good thing.

After all, that maintenance programmer is going to be you one day.