Sometimes you need to take a step back from a problem, to see the forest for the trees.
GeekWeaver was being held up by something that seemed a rather complicated knot; one that I’ve wrestled with a number of times but never really untangled to my satisfaction.
So last night I decided to restart with a clean slate. I didn’t look at the existing code or existing unit-tests. Didn’t even open my IDE or project file.
I just started up IDLE and in a single file, redid the whole thing from scratch, in a fast test-driven stylee.
Amazingly I think I’ve come out with a cleaner solution, messing around with fewer classes and no attempt to over-re-use with inheritance. The whole thing took about two hours total. Of course, it’s not quite finished, and still needs to be integrated back into the main codebase. But I like it a lot more. It’s shorter and easier to understand.
Sometimes (at a certain granularity) old code *is* more of a burden than an asset. Understanding what it does and what you can do it is a cognitive cost that outweighs its value. Don’t be afraid to throw code away when you need to.
Caveat for small granularities. Obviously rewriting an entire application from scratch is a different matter.
A WikiDE is, of course, something I’ve been working on in the background for some time. But I’m far from having anything to show yet. So if these guys get there first, good luck to them.
I just want to be able to start working this way.
Damien Katz has more interesting comments about Erlang’s “ugliness”.
I’m way too busy now … but I’m having some kicking ideas about my own grandiose bid to improve programming …
… think GeekWeaver in an SdiDesk-alike editor (obviously).
Then imagine that *everything* is a template.
That’s the way that GeekWeaver is already going. Everything is a template (ie. has named slots that can be filled). Function calls are just the injection of a data-block into that template. Another way of putting it, all objects know how to handle the “call” message with a data-block as argument, even if they don’t do anything very useful with it.
But now imagine that all the types of things you can get in SdiDesk … text pages, grids, network diagrams, are also templates. And you can plug and pipe them together any way you like. One page can hold a table, another a network diagram-shaped template, and a third can be specified as the result of injecting the first into the second.
Hmmm … this definitely looks like it’s going in the right direction.
Here’s a question … why is Erlang so ugly?
I don’t mean that in a pejorative way (not much, anyway). I mean, I really love what it does. I’m totally impressed with Erlang’s power and simplicity. I’m writing simulations which are about a quarter of the size of the Python equivalent. So this is not to be taken as a criticism of Erlang which I’m definitely committing myself to, this year. Rather this is some random speculation about programming language aesthetics.
Erlang is wonderfully concise. And yet, somehow, unlike Python, unlike Haskell, it just doesn’t come across as beautiful. It’s confusing. It looks cluttered.
A couple of lines look fabulous. But the simplicity doesn’t scale.
At first guess, there seem to be three issues.
a) As people have noted, the record type is ugly. It is. And counter-intuitive to use in patterns (although I may just be stupid).
b) In general I think it’s good and brave thing to take a stance *against* objects. But I haven’t figured out how to do encapsulation (data-hiding, abstract types)
Sure, I can define polymorphic functions (one clause at a time per input type) which is a lot shorter and more powerful than overloaded methods in Java. But it has the effect of jumbling all my data-types together. Which just feels *wrong* to me. (Of course, maybe that’s some residual OOness in my thinking.)
But I think that may be part of the bigger issue :
c) erlang doesn’t seem to have resources for “programming in the large”. And, ironically, because erlang is so powerful, that problem becomes visible at a smaller scale – precisely because in erlang “large” programs are actually “small”.
Or rather, the only resource is “modules” (which means breaking up into multiple files – always an extra overhead.)
But if you avoid breaking things up into files, the opposite problem becomes apparent. I can do the equivalent of a small Java class (let’s say something around 50-80 lines) in about 6 to 10 lines of Erlang. But 10 lines of erlang is too small for a separate file. So I’ll add the next 10 line packet of functionality to the same file. By the time I’m up to 4 or 5 packets that would be handled as different classes in Java or Python I may have written only about 50 lines of code … but it’s all running together!
There’s no higher level of organization to distinguish and separate the code. In Python I often put 5 or 6 small-medium classes in a single file or around 300-500 lines. But the indentation and editor make these reasonably distinct and identifiable. In contrast, my equivalent 200 lines of Erlang have no visual cues to break them up. I can’t use functions as a visual element because pretty much every line is a new function (except when I’m doing I/O, which has its own “issues”).
I’m left with using comments but my editor (Komodo), excellent in many ways, doesn’t actually know Erlang and so doesn’t colour them differently. And, in general, because functions are powerful, they *are* short : one or two lines. But those lines are typically much denser than Python. Even if a dedicated editor would colourize them, I’m not convinced that’s such a big win at this density. On the other hand, I don’t want to artificially scatter them out into multiple lines. I’m not trying to recreate Python with a slightly less appropriate syntax. I want to take advantage of Erlang’s power and conciseness.
But I wonder what the right aesthetics for a language as high level, dense and abstract as Erlang is. Haskell looks cleaner to me – maybe because it does abstract data-types right. But can it solve the problem of organizing your larger-scale things? Lisp is no role-model. ML and its offspring have always repelled me visually. (Nothing can be more ugly, dispiriting and patronizing in a programming language than an explicit “begin” statement.)