I am coding a meta-circular interpreter and am trying to implement closures. I have a function make-lambda which makes the closure:
(define (make-lambda parameters body env)
(list 'lambda parameters body env)
)
And a function which handles definitions in which I have a check to see if the definition contains a lambda in which case I would need to create a closure:
(let* ((closure (make-lambda (cadadr defn) (cddadr defn) env)) ; creates a closure
(var (car defn))
(binding `(,var . ())))
(display closure)
(newline)
(display "CLOSURE BEFORE: ")
(display (cadddr closure))
(newline)
(set-car! env (cons binding (car env)))
(display "CLOSURE AFTER: ")
(display (cadddr closure)) ; why is this different?
(newline)
;(set-cdr! binding (meta-eval error (cadddr closure) ))
;(set-cdr! binding closure)
(display "NORMAL: ")
(display env)
(newline)
)
I cannot seem to figure out why cadddr closure is different before and after the set-car! call. Any help would be appreciated.
I have tried all sorts of troubleshooting and have some in the code above and still do not know what is going on.
The
cadddrofclosureis another pointer toenv, as you can see from the definition ofmake-lambda. Since you have modified the list pointed to byenv, all references to it, bothenvand(cadddr closure), will reflect the changed list.