leah blogs

August 2004

05aug2004 · Bluemoon

This is a proposal for a new programming language.

Serious warning: Reading this post may rot your brain in severe ways. I find myself—being the designer of this language—having serious trouble writing stack oriented code in languages like Forth or PostScript. But feel free to go ahead if you don’t care for these languages…

This new language, dubbed Bluemoon, aims for high goals: It should be as powerful as Lisp (the goddess of all languages :-)) without it’s problems, for example the—to the eyes of many—quirky syntax. s-expressions were made to be read by computers, not to be written by humans. (At the same time, Bluemoon also drops list processing from the absolute core.)

A Bluemoon program has—as a Lisp one—just about no syntax. It is a list of tokens, with only a few are special (comparable to Common Lisp reader macros).

To show a non-trivial example, let’s write the classical example used for closures, a counter:

def :counter {
  def :count 0
  { set :count dup + 1 count }
}

def :a counter
print a  # => 1
print a  # => 2
print a  # => 3

This Bluemoon program would look like that in Ruby:

def counter
  count = 0
  lambda { count += 1 }
end

a = counter
p a.call  # => 1
p a.call  # => 2
p a.call  # => 3

Or in Scheme:

(define (counter)
  (let ((count 0))
    (lambda ()
      (set! count (+ count 1))
      count)))

(let ((a (counter)))
  (display (a))
  (display (a))
  (display (a)))

Let’s examine the example above a bit more. Bluemoon is a fully object-oriented language (the exact semantics of it’s object-orientation are not fully specfied, however). Therefore, def is not a special directive or a special form, but just a method defined for symbols. Symbol#def therefore “takes one argument” (more on that below) and binds the block given to its symbol, in this case creating a toplevel definition.

Symbol#def is not specfic to blocks, as you can see in the second line, it’s very much like Scheme’s define. It creates a lexical variable, which can be “overwritten” using Symbol#set.

One thing I didn’t tell so far: Bluemoon is stack oriented. And now we get to the syntax quirk I’ve warned you before.

This is an idea inspired from APL. In general, stack based languages like PostScript and Forth are read left-to-right. This leads to postfix code. For example, in Forth:

2 2 + .  # => 4

In Scheme, which is infix, this program would look like:

(display (+ 2 2))  # => 4

And therefore, in Bluemoon (infix too):

print + 2 2

This is due a nice parsing hack: In Bluemoon, “lines” are read from right-to-left, as in APL. This makes the language IMHO a lot easier to read, and is less confusing to people coming from other languages. (But can drive you nuts if you need to write PostScript or Forth.)

This is how the parser will read the counter code:

  1. Push a Block
  2. Push a Symbol
  3. Look up def
  4. Call Symbol#def

This is it, the language of Bluemoon is more or less defined.

Now, there is quite a problem: There is no implementation by now. :-) I think I’ll write a simple interpreter in the next weeks, but a lot more will need to be done to make the language usable:

  • define a standard library (Ruby’s will be a great inspiration source to me)
  • define the object-oriented semantics (this will take some experimentation)
  • a compiler?

Not to speak of a community and loads of libraries… ;-) But let’s have everything in sequence.

NP: Black Monday—Fixated

Copyright © 2004–2022