guile-devel
[Top][All Lists]
Advanced

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

Re: memoization and error messages


From: Dirk Herrmann
Subject: Re: memoization and error messages
Date: Thu, 28 Nov 2002 19:02:49 +0100 (CET)

Hello Daniel,

thanks for your comments.

On Sun, 24 Nov 2002, Daniel Skarda wrote:

>   Why I think it is good for macros to be "first class objects":
> 
> >  guile> define
> >  ERROR: In procedure memoization:
> >  ERROR: Misplaced syntactic keyword define.
> >  ABORT: (syntax-error)
> 
>   Does it mean that `define' is unbound? (*) I do not think so - I guess R5RS 
> does
> not allow to have macro and variable of the same name. 

R5RS does allow macro and variable of the same name - in a sense.  For
example:

(defmacro foo <...>)  ;; after this line, foo is a syntactic keyword
(foo some-args ...)   ;; foo will be expanded.
(define foo <some-value>)  ;; after this line, foo is bound to a location
(foo some-args ...)   ;; foo will not be expanded.
(define (bar) foo)    ;; bar will refer to foo's binding
(defmacro foo <...>)  ;; after this line, foo is a syntactic keyword, but:
                      ;; bar will still refer to foo's _variable_ binding
(bar)   ;; will return the value at the location of foo's variable binding
(foo some-args ...)   ;; foo will be expanded
(define foo <some-value>)  ;; after this line, foo is not a syntactic
                           ;; keyword anymore.  I guess that this define
                           ;; should actually become a set! and should
                           ;; change the content of the location to which
                           ;; foo was bound formerly.
(bar)                      ;; If my above guess is right, this function
                           ;; should now return the value of the latest
                           ;; define.

>   Macros should be in the same namespace as variables are. This is what I
> dislike about Common Lisp - it has one namespace for functions and another for
> variables. Maybe this is just a programmer's taste - but in my opinion
> programming languages should not be designed with "what is easy to implement"
> idea in the mind, but rather "programming should be fun". And I do not think 
> it
> is fun to add new cases users have to handle.
> 
>   These things I would like to be able to write in guile:
> 
>   (if (defined? 'my-macro)
>       ....)

Well, this could still be done.  The question, however, is, whether one
should distinguish between defined? and syntactic-keyword?.

>   (if (macro? foo)  ; not possible with your modification
>       ....)

True, but if you would quote foo, this could still be checked.

>   (define old-foo foo) ; also not possible

But
    (defmacro old-foo args `(foo ,@args))
does the trick.  The only problem that we currently have, is that defmacro
is not able to keep track of the module the definition of foo came from.  
For a temporary workaround, see my email about preparation for hygienic
macro expansion.

>   (defmacro foo args
>     (do something clever with 'old-foo args))

As long as you don't mix up definitions of foo from different modules,
this would also work with my example above.  And, with the workaround
presented in my email about preparation for hygienic macro expansion, it
should be possible to cover all cases even while we don't have a real
hygienic macro expander.

>   (module-ref (resolve-module '(guile-user)) 'define)
>     
>     ; returns the same value as simple "define" - but one line is correct
>     ; another would be error. Why?

Who says that one line is correct and one is an error?  sure:
   guile> define
_would_be_ an error if my local version of eval became official.  Today's
guile still accepts such a line, as it also accepts the module-ref code.
If my changes became official, the behaviour of module-ref with respect to
syntactic keywords might also change.

That is, it is simply not sure that module-ref will work the same way.
However, I recommend again to look into the email cited above.

>   3) Provide macro `dynamic-expansion' - maybe something like this:
> 
>       (defmacro dynamic-expansion code
>          `(local-eval '(begin ,@code) (the-environment)))
>     
>       so it would be easy to identify the code with dynamic macro expansion. 
> (I
>     do not know why people use dynamic macro expansion, but I guess it is 
> handy
>     during macro debugging...)

Yes, this could be done, although I recommend that we get rid of
local-eval.  The goals above can also be accomplished the following way:
Use 'eval to create a closure, with an argument for every element of the
local environment that is needed within the closure.  (Note:  This does
not allow to set! elements of the local environment.  You have to modifiy 
this approach a little to emulate a set! behaviour.  It's more effort, I
agree.)

Maybe we are just discussing the wrong examples here:  The major issue
about first class macros is that you can define them at run-time.  That
is, you could at run time change the set of syntactic keywords and have
the same code code expanded in different ways depending on the set of
macro definitions defined at run-time.  Do you have any situations like
this in mind?

Best regards
Dirk Herrmann





reply via email to

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