Pascal Costanza <pc@p-cos.net> wrote:
+---------------
| Rob Warnock wrote:
| > In Scheme, this is legal:
| > > (letrec ((a (lambda (x) (+ x 3))))
| > (let ((old-a-result (a 2)))
| > (set! a (lambda (x) (+ x 17)))
| > (list old-a-result (a 2))))
| >
| > (5 19)
| > >
| > The same [well, ignoring SET! vs SETF] wouldn't work with
| > your dual value/function LETREC [you get (5 5)],
|
| No, I really get the "correct" result:
| > (defmacro letrec ((&rest bindings) &body body)
| `(macrolet ,(loop for (var) in bindings
| collect `(,var (&rest args)
| `(funcall ,',var ,@args)))
| (let ,(mapcar #'first bindings)
| (setq ,@(mapcan #'copy-list bindings))
| ,@body)))
|
| > (letrec ((a (lambda (x) (+ x 3))))
| (let ((old-a-result (a 2)))
| (setq a (lambda (x) (+ x 17)))
| (list old-a-result (a 2))))
| (5 19)
+---------------
*OOPS!!* Right you are!! My most abject apologies!! I'm
afraid I only skimmed your LETREC macro the first time
I saw it, and somehow totally missed the embedded FUNCALL!
[I somehow misread it as a set of FLETs parallel to the LETs.]
Of *course* it works "correctly"!
"Never mind..." (*blush*)
-Rob
p.s. That MACRLOET expanding to a FUNCALL of a variable
[maybe a global, maybe a local] is a clever trick. I'm
going to remember that one. I can think of a bunch of
other situations in which to use it...
-----
Rob Warnock <rpw3@rpw3.org>
627 26th Avenue <URL:http://rpw3.org/>
San Mateo, CA 94403 (650)572-2607