Subject: Re: Controlling the expansion of a macro
From: Erik Naggum <erik@naggum.net>
Date: 2000/07/04
Newsgroups: comp.lang.lisp
Message-ID: <3171730586141518@naggum.net>

* lnp@healy.washington.dc.us
| I would like to define macros whose expansion can be controlled by a
| enclosing form.
:
| The only solution I have come up with is to use macrolet, e.g.
| make a new macro
|   (defmacro plusminus-int (a b pm)
|     (if pm
| 	`(+ ,a ,b)
|       `(- ,a ,b)))
| then macrolet plusminus in the wrapping macro,
|   (defmacro adding-all (&body body)
|     `(macrolet ((plusminus (a b) `(plusminus-int ,a ,b t)))
|        ,@body))
| now the form
|   (adding-all (foo (* (bar (plusminus x y)) (plusminus z w))))
| will expand correctly.

  Why the complicating plusminus-int?  You may define the macro body
  directly:

(defmacro adding-all (&body body)
  `(macrolet ((plusminus (a b) `(+ ,a ,b)))
     ,@body))

| While this approach works, it would be clumsy for the application I
| have in mind, because the controlling variable has to be passed
| along in the lambda list.  Is there a "special variable" type of
| approach that I can use, or is this just dreaming?

  Well, I don't see why you need it in this case.

| Side question: In ACL, the scope of a macroletted name encompasses the
| macro definitions themselves, rather like a labels instead of a flet.
| Is this standard? (CLHS doesn't seem to say, but I may not be reading
| it correctly.)

  It is my understanding that this is mandated by the standard.

| Since recursive macros are disallowed ...

  Are they?

| Side question:  Symbolics had a compiler-let which maybe would solve
| this problem?  Is there an equivalent in ANSI CL?

  Not in ANSI CL, but in Allegro CL, you have excl::compiler-let.
  It can be indispensable in certain situations.

#:Erik
-- 
  If this is not what you expected, please alter your expectations.