guile-devel
[Top][All Lists]
Advanced

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

Re: Macro uexpansion


From: Mikael Djurfeldt
Subject: Re: Macro uexpansion
Date: 19 Dec 2000 20:19:48 +0100
User-agent: Gnus/5.0807 (Gnus v5.8.7) Emacs/20.7

Craig Brozefsky <address@hidden> writes:

> Mikael Djurfeldt <address@hidden> writes:
> 
> I may have developed the reputation of the Common Lisp pundit during
> the last few threads about object systems

Common Lisp pundits are very much appreciated.  There's no reason to
redo all thinking and collection of experience that has gone into
Common Lisp.

> > Macro unexpansion seems to amend this a bit.  For example, the
> > behaviour of a function FOO using a macro BAR won't anylonger be a
> > function of when or if the definition of FOO has been evaluated, but
> > solely depend on the current definition of BAR.
> 
> Macros are programs, programs which produce another program.  A
> program's result depends upon the environment it is evaluated in.  It
> seems that macro unexpansion changes the environment a macro program
> is evaluated in, and therefor changes the results.  It does this by
> collapsing the (re)definition and evaluation time of the macro into
> the same event, and it doesn't do that consistently either.
> 
> I worry that macro unexpansion might introduce more issues for
> developers than it removes.  The seperation of (re)definition and
> evaluation time is a useful feature of macros.  A simple example is a
> macro that expands into different things depending on wether *debug*
> is bound to T or NIL.  A redefinition, and I'm not sure if unexpansion
> only "unexpands" when the macro has actually changed (good luck
> defining what that means) or "unexpands" whenever its definition is
> re-evaluated, could do things like turn off debugging in all the
> previously loaded code which used that macro, despite the fact that
> the programmer made sure *debug* was bound to T when loading them and
> expects them to have debugging code inserted.
> 
> Remember, macros aren't just function's that don't evaluate their
> arguments, they are programs that produce programs.  It might be
> better to not make their evaluation time and environment nearly
> arbitrary.

Both evaluation time and environment of macros are well defined in the
syntax-case macro system independently of this discussion:

* evaluation time for macros is any time

* environment for the macro is any top-level environment supplying
  at least the R5RS bindings and with a guarantee that all top-level
  macros is expanded in the same environmnet

By definition we don't know when and exactly in which environment
macros are evaluated.  The main reason is to allow for macro expansion
during both compilation and interpretation without change in
semantics.

The effects of the suggested use of the unmemoization protocol for
unexpansion will have these effects:

Macro user: No change in semantics from the one defined in the
syntax-case system.

Macro writer: Even though one instance of a macro transformer is
invoked only once for each use of the macro, different instances might
be invoked for the same use, even if the expression containing the use
hasn't been re-evaluated.

The last rule might seem complicated, but is rather simple.  A more
restrictive version which includes the last rule is:

A given macro use can be expanded multiple times.

Concerning your debug example, I think it could be seen as a strength
to be able to switch off the debugging code in all places referring to
one particular variable.  It also seems simpler to think about than
remembering *when* various parts of the system were loaded.

So, with these three rules, we're safe:

1. No guarantee about evaluation time

2. No guarantee about environment (except it's the same for all
   top-level invocations in the same module)

3. No guarantee about the number of times a use is expanded

This kind of "no guarantees" is actually a strength of a language
since it gives flexibility to the implementor and to future
development.



reply via email to

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