Friday, October 27, 2006

Lambda calculus, Smalltalk, and you

So... after thinking about the whole issue of types for quite a bit... I have to say that I am happy I work with Smalltalk. But the reason why is interesting, because I think it's more than just some sort of "it struck my fancy".

From the label experiment and the conversations with Dan Ingalls, I gathered the fact that when designing a language, it is important that it does not have too much stuff in it. This is because whatever you put in the language, you will have to mess with via a computer interface. And this makes interacting with it slower, in the same way that hard drive access causes considerable lag for a modern CPU.

In short: the more stuff a language has, the slower the interaction with it will become.

Now, since productivity is one of the values I care about, I cannot help reaching the conclusion that I want a language with the least possible stuff so I can be most productive with it.

So what is this least possible stuff? Well, if a language had nothing, then everything would be in our mind, and this is an issue because then we don't take advantage of the computer, and we also overflow the rather scarce 7 plus minus 2 slots of scratch ram we come with.

Therefore, a balance must be chosen such that what stresses our scratch ram the most stays there, and what stresses our scratch ram the least goes into the computer. Language design is a register allocation issue.

Consider then lambda calculus. If we're reasonably trained to do natural deductions in logic, then adding lambda calculus does not seem like that much of an additional imposition. Putting lambda calculus annotations in the computer however causes human interface traffic because in order to think in one's mind, one has to make reference to stuff in the computer. We can cache all we want by remembering, but eventually we will hit the hard drive and then our overall productivity will go down just because of the particular register allocation model we chose.

Therefore: do lambda calculus in one's mind together with the logic. Then, simply store the results of all this calculation in the computer. And do it in a way that makes it easy to reconstruct the deductions and lambda calculus annotations on demand, but without resorting to verbose artifacts that cause human interface chatter. In other words, be intention revealing.

Enter Smalltalk. No type explicit annotations of things we do in our minds, just one of the places where expressing results of deductions with type annotations is easy. Because, as we know, when we write Smalltalk we think about types in the sense that we have to keep track of what messages will be sent to what objects.

I insist that by designing a network of objects such that each local evaluation context fits in our scratch ram, and such that the chaotic interaction of the parts is designed in such a way that the overall system has the emergent property of solving the problem at hand, is (one of) the most efficient ways to get things done. This is just because working this way implies taking advantage of a human friendly scratch ram register allocation strategy.

Watch how you think, run a time profiler in your daily work, and see where the time is going. If most of it goes to clicks, typing and reading, then you have a register allocation issue. Then, solve it by allocating your registers more appropriately, and then training yourself to take advantage of the new register allocation. Most brain cycles should be going into design anyway.

Eventually this will drive the language you choose to work. And the good thing is that Smalltalk is just one option... and even if it were and you happened not to like it, you can change it to your heart's content.

I find myself very productive in Smalltalk. How about you? :)


Isaac Gouy said...

Dan Ingalls: Object-Oriented Programming, 1989

41 minutes

David Ungar Type declarations were one thing which we were going to talk about...

Dan Ingalls Smalltalk does not have any type declarations nor does Self. There isn't any reason that there can't be type declarations, I think; but it's a different situation. Conventional strongly typed languages type according to what I would call concrete types and in an object oriented language you can still assert type declarations but what you want to assert is what I would call the abstract type - in other words you want to assert that this is an object which understands the following protocol and then if you do that it gives you the same kind of security that people like to feel about code that they have written, which is you've asserted what all those things are and therefore the code shouldn't break for that reason.

I think there's still a philosophical dispute about whether that solves the whole problem; you know, have you nailed down every possible leak if you have declared the type; and obviously that's not so, because you have values that are out of range and all this other stuff.

David Ungar People who like type declarations would have to get used to writing more abstract declarations than they do now...

Dan Ingalls That's right but I don't think it would be any problem. I actually did a type system once with Alan Borning for Smalltalk. It didn't turn out to be sound; but we did get a chance to use it and it felt completely natural, and it added the kind of readability - people say that it makes code more readable because you know kind-of what you can expect. I think that's true to a certain extent.

Darius said...

But, when you optimize your mental registries, how do you efficiently convey all this to your future self, to other programmers with different experiences, and to Jr. programmers who haven't achieved your metal registries yet? The "code" is not a good reflection of your thinking and what you choose "not" to implement. The same goes for any "type system" too. Your optimization now creates a bottleneck between networked and time shifted minds, which arguably is the most import thing above all including more important than code that's just working correctly. It seems that the "coding tools" on creates for one's self and for others more accurately describes one's mental registers than one's code.

Have you heard this interview by Jon Udell?
Software factories: a conversation with Ward Cunningham and Jack Greenfield

Andres said...


Some of the ways to hint at what people were thinking when they wrote code are well known. Collectively, they are frequently referred to as being "intention revealing", or following good "design patterns", and such.

I am not sure the coding tools reflect the mental register allocation. Perhaps the code itself does (if written carefully).

The bottleneck you refer to happens to all of us when we think. Clearly, other people didn't experience our thought process, and so they do not have access to our scratch ram representation of an idea.

With practice, however, one becomes good at understanding other people's ideas. This is normal --- it is one of the things education is supposed to take care of.