Alan Malloy <a...@malloys.org> writes:

> It seems to me that it would be nice to have macros automatically
> include, on their result forms, the metadata from their input
> &form. Of course, macros may wish to add metadata as well, so the two
> maps should probably be merged. However, there are certainly some
> problems with this approach: for example if a macro wants to return
> something that can't suppport metadata (like an Integer), the compiler
> needs to be careful not to try to include it. So I'm hoping the
> community can comment on whether this feature would be useful, or
> whether there are fundamental problems with it that I haven't
> foreseen. Is there a reason this can't make it into a future version
> of Clojure?

I think this is an excellent idea.  Overall I believe this reduces the
number of situations in which one needs to be actively aware that a
particular expression will be subject to macro-expansion.  The
alternative-world where the 99% of well-behaved macros returning IMetas
manually forward metadata from &form seems like a world with way too
much boilerplate to me.

Forwarding metadata does preclude macros which use metadata applied to
&form as parameters and construct new metadata which may not include the
literal values specified in the user-supplied metadata.  I'm not sure
this is a good idea anyway, but this sort of case -- and any others
where metadata should not be forwarded/merged -- could easily be
supported by providing a variation of defmacro with the current
behavior.  Or perhaps by configuring the metadata-forwarding behavior
via metadata on the macro var -- something like:

  (defmacro foo {:forward-meta false} ...) ;; or,
  (defmacro ^:replace-meta foo ...)

If a macro expands to something which doesn't implement IMeta, then I
believe the compiler needs to error out if metadata is applied to it,
just as it does applying metadata to non-IMeta literals.  To do
otherwise would be inconsistent, and result in the same silent data-loss
as macros are yielding today.

This proposal doesn't touch forwarding metadata on forms which become
macro arguments, obviously.  There's still room for inconsistency there,
but I think that's clearly in the court of individual macro authors to
implement the correct behavior.

Are there other contexts where metadata should potentially be forwarded?
I don't know how often this comes up, but:

  (=  (meta ^:foo (quote foo)) (meta (quote ^:foo foo)))
  ;; => false

-Marshall

-- 
You received this message because you are subscribed to the Google
Groups "Clojure" group.
To post to this group, send email to clojure@googlegroups.com
Note that posts from new members are moderated - please be patient with your 
first post.
To unsubscribe from this group, send email to
clojure+unsubscr...@googlegroups.com
For more options, visit this group at
http://groups.google.com/group/clojure?hl=en

Reply via email to