guile-user
[Top][All Lists]
Advanced

[Date Prev][Date Next][Thread Prev][Thread Next][Date Index][Thread Index]

Re: Injecting variables into closures.


From: Kjetil S. Matheussen
Subject: Re: Injecting variables into closures.
Date: Thu, 29 Nov 2007 16:52:08 +0100 (CET)



On Thu, 29 Nov 2007, Clinton Ebadi wrote:

"Kjetil S. Matheussen" <address@hidden> writes:

Hi,

I need (well) to inject variables into closures, and have
come up with the following macro to do so:

(define-macro (inject-variable name value)
  (define env (gensym))
  (define closure (gensym))
  (define vars (gensym))
  (define secondname (gensym))
  (define secondval (gensym))
  (define first-env (gensym))
  `((procedure->macro (lambda (,(gensym) ,env)
                        (cond ((null? (cdr ,env))
                               (let ((,closure (car ,env)))
                                 (set-car! ,env (cons ',name ,value))
                                 (set-cdr! ,env (list ,closure))))
                              ((null? (null? (cdr (car ,env))))
                               (let* ((,vars (car ,env))
                                      (,secondname (car vars))
                                      (,secondval (cdr vars)))
                                 (set-car! ,env
                                           (list (list ',name firstname)
                                                 ,value ,secondval))))
                              (else
                               (let ((,first-env (car ,env)))
                                 (set-cdr! ,first-env
                                           (cons ,value (cdr ,first-env)))
                                 (set-car! ,first-env
                                           (cons ',name (car ,first-env)))
                                 (set-car! ,env ,first-env))))))))


(let ()
  (display (defined? 'gakk))
  (inject-variable gakk 90)
  gakk)
=> #f90


Now I wonder, is this safe and portable? Or are there
other and better ways to do this?

Manipulating the environment is not going to be portable or safe. In

Well, it doesn't have to be. But I understand very well why
its not. :-)



addition procedure->macro should be deprecated (but appears not to
be?), and will be removed (necessarily) whenever someone finishes the
phase separation in the evaluator.


Hope its not going to be. Its a convenient function.



Is there a special reason to inject a value into the environment
rather than let binding it?


I'm just playing with making a prettier module system:

(define-namespace bank)

(def-bank sum 0)
(def-bank (inc n)
  (inc! sum n))
(def-bank (dec n)
  (inc sum (- n)))

(bank/inc 50)
(bank/sum)
=> 50


I can also do it by doing a complete source transformations,
replacing sum with bank/sum everywhere and so on, but I would
rather avoid doing that.

Its just for fun.





reply via email to

[Prev in Thread] Current Thread [Next in Thread]