Sunday, July 23, 2006

RLisp gets basic OO support

Update on state of RLisp. Using Ruby metaprogramming facilites it's possible to do some basic OOP in RLisp:
$ cat examples/class.rl
(let Point [Class new])
[Point attr_accessor 'x]
[Point attr_accessor 'y]
[Point define_method 'to_s
 (lambda x
 (+
     "<"
     [[self x] to_s]
     ","
     [[self y] to_s]
     ">"
 ))
]
(let a [Point new])
[a x= 2]
[a y= 5]
(print a)
$ ./rlisp < examples/class.rl
<2,5>
And it has hash tables:
$ cat examples/hash.rl
(let ht [Hash new])
[ht set 'a 2]
[ht set 'b 4]
[ht set 'a 6]
(print (+ [ht get 'a] [ht get 'b]))
(print ht)
$ ./rlisp.rb <examples/hash.rl
10
{:a=>6, :b=>4}
Iterators:
$ cat examples/iter.rl
(let a '(1 2 3))
(sendi a 'each
 (lambda (i)
     (print i)
 )
)
$ ./rlisp.rb <examples/iter.rl
1
2
3
Lists (car/cdr/cons do not share storage, they create a new list):
$ cat examples/array.rl
(let a [Array new])
(print (car '(1 2 3)))
(print (cdr '(4 5 6)))
(print (cons 7 '(8 9)))
[a push 1]
[a push 2]
[a shift]
(print a)
$ ./rlisp.rb <examples/array.rl
1
(5 6)
(7 8 9)
(2)
And (drum drum drum drum) it even has macros:
$ cat examples/macro.rl
(defsyntax cond args
 `(if (>= (length ',args) 2)
      (if (eval (hd ',args))
          (hd (tl ',args))
          (cond ,@(tl (tl args)))
      )
      (if (eq? (length ',args) 1)
        (hd ',args)
        nil
      )
 )
)

(defun sign (x)
 (cond
     (>  x 0) 1
     (== x 0) 0
     -1
 )
)

(print (sign 42))
(print (sign 0))
(print (sign -8))
$ ./rlisp.rb <examples/macro.rl
1
0
-1

1 comment:

  1. Anonymous23:04

    In some obscure way I find this being really cute...

    ReplyDelete