I know I'm a heretic for even daring to mention things like alternative
syntaces for Smalltalk, but I've currently got a little
thought-experiment of designing a language with extremely intuitive
syntax for building abstractions, and because Smalltalk is a good point
to start at, I'm trying to improve on SmalltalkSyntax
. While not as
syntax-heavy as C++ or even Java, Smalltalk still has much more syntax
(and thus more that has to be learned on that side) than, say, Lisp or
Some of these syntactic changes will also change the semantics of the
language. It would be nice if people more familiar with Smalltalk than
myself would comment on their implications: for instance, if losing some
specific syntax will make some nifty programming idiom hard or
The ideas are:
0. abolish the difference between parenthesised expressions and blocks.
A parenthesized block would execute all statements contained therein; returning the last statement, I assume?
(yes, quite consistently with the idea of abolishing ^, below.) What of empty parens? Might be a good shortcut for self.
(I don't know, I don't have any useful (and intuitive) semantics for empty parens in this scenario.)
Both parentheses and blocks contain code to be executed. With blocks, it is deferred and may take parameters; with parentheses, it is immediately executed and may not take parameters. It should be easy enough to defer only those parenthesised expressions that do not take parameters, or even all parenthesised expressions (using them as message
receivers would then force them to be evaluated.)
Are parenthesized expressions objects in this scheme? It appears not.
Yes, they are. They are blocks, and blocks are objects; but for example, nullary blocks could have a unary #value message that would force them to be evaluated...
1. define blocks with inline, rather than separate, variable declarations.
[ :foo :bar | foo for: 'life' frobnize: bar ]
( :foo for: 'life' frobnize: :bar )
or even, Arc-like
( _ for: 'life' frobnize: _ )
The syntax for these "inline variable declarations" could be something
else. For example, instead of using colons, names beginning with
lowercase letters might always be variable names.
2. call blocks with descriptive, rather than generic, messages.
For example, if myBlock contained the block given in the previous point,
myBlock value: aFoo value: aBar.
myBlock foo: aFoo bar: aBar.
Arc-like block definition could use the default message name, value:.
This would enable users to bind block parameters in different orders.
Moreover, the code looks cleaner. There is a nice symmetry in foo: x
3. replace assignment with a set: message for symbols.
a := 3
#a set: 3
Probably instance variables should have some special syntax. How
about this (used by Self, I reckon?):
address := anAddress
4. abolish syntax for local variables.
Assignment is mostly needed in connection with local variables. Local
variables are already better handled by using blocks; for example,
|foo| foo := 2*bar. self speed: foo
(self speed: :foo) foo: 2*bar.
If this "postfix binding" seems too weird or cumbersome, we could
introduce a "prefix message" syntax:
foo: 2*bar (self speed: :foo)
5. get rid of ^.
Rather, just return the value of the last statement. If one wants to
return "self", that's easy enough to write on the last line.
name := newName
(setting instance variables could also return self so the explicit self would be
You really don't understand ^ if you think it's even possible, let alone a good idea, to eliminate non-local returns.
I don't pretend to
understand Smalltalk very well. I'm just using it as a basis for this thought-experiment. I'd like to see an example of a method that benefits a lot from ^.
And what justification do you give for it? Just that Smalltalk doesn't return the value of the last expression, which is something completely independent of non-local returns.
Further, ^ can be turned into a message just as easily as :=. ^ is a message send to thisContext to unwind the stack.
Well, I'm trying to drop off special syntax that seems unnecessary to
me. The hypothesis is that all syntax adds to the effort of learning a language. That hypothesis is challenged below ->
See also SyntaxVsSemantics
for an explanation of the distinction between bad syntax and good syntax. You assume that having less syntax is automatically a good thing. It is not. For example, Lisp's lack of special syntax for lambdas is evil as far as I'm concerned. And your reinventing Lisp in Smalltalk isn't particularly inventive.
I'm not assuming less syntax is automatically a good thing, but I think in general it is. The precise reason I'm asking here about this is that I hope people to point out situations where this decrease of syntax does not pay off. I'm not trying to score points off inventiveness, either.
On a less related track, Lisps have a lot of special syntaxes for lambdas. For example, (defun) is one. Or of course, it depends on what you consider "syntax".
Of course I'm trying to invent good syntax. As I state at the beginning of this page, the purpose is to provide intuitive syntax for abstractions.
See also SmalltalkLanguage