[Date Prev][Date Next][Thread Prev][Thread Next][Date Index][Thread Index]
Re: Access to lexical environment?
I am not sure how to properly develop simple extensions to Lisp
syntax (using CL). For example, suppose that I'd like to set up a
way to create new things that has the following (familiar) syntax:
(def-newthing fred (other-thing) ((n :initform (+ a b))
(ls :initform (rest ls1)))
...etc.)
The mechanism in Lisp for capturing the lexical environment is LAMBDA.
Try this
(defmacro def-newthing (name superthings specs)
`(progn (setf (getf ',name 'superthings) ',superthings)
(setf (getf ',name 'slots)
(list ,@(map 'list
(lambda (spec)
(destructuring-bind (name &key initform) spec
`(list ',name (lambda () ,initform))))
specs)))))
(def-newthing fred (other-thing) ((n :initform (+ a b))
(ls :initform (rest ls1))))
==> (PROGN (SETF (GETF 'FRED 'SUPERTHINGS) '(OTHER-THING))
(SETF (GETF 'FRED 'SLOTS)
(LIST (LIST 'N (LAMBDA () (+ A B)))
(LIST 'LS (LAMBDA () (REST LS1))))))
I hope this clarifies the situation for you.
The following version evaluates better and conforms to CLtL:
(defmacro def-newthing (name superthings specs)
`(progn (setf (get ',name 'superthings) ',superthings)
(setf (get ',name 'slots)
(list ,@(map 'list
#'(lambda (spec-list)
`(list ',(car spec-list)
#'(lambda () ,(caddr spec-list))))
specs)))))
def-newthing
[2] What?.. (pprint (macroexpand '(def-newthing fred (other-thing)
((n :initform (+ a b))
(ls :initform (rest ls1))))))
(progn
(setf (get 'fred 'superthings) '(other-thing))
(setf (get 'fred 'slots)
(list (list 'n #'(lambda ()
(+ a b)))
(list 'ls #'(lambda ()
(rest ls1))))))
-- ck
+-----------------------------------------------------------------------------+
| Cris Kobryn UUCP: {sdcsvax|seismo}!esosun!kobryn |
| Geophysics Division, MS/22 ARPA: esosun!kobryn@sdcsvax.ucsd.edu |
| SAIC SOUND: (619)458-2697 |
| 10210 Campus Point Drive |
| San Diego, CA 92121 |
+-----------------------------------------------------------------------------+