Eli Barzilay wrote: > Three hours ago, Mark Engelberg wrote: >> On Thu, Jul 14, 2011 at 4:35 AM, Thomas Chust <ch...@web.de> wrote: >>> While Clojure *mitigates* the problems of non-hygienic macros >>> using namespaces and a shorthand syntax for freshly generated >>> identifiers, it doesn't *solve* the problems. Racket's macro >>> system, on the other hand, does solve the problems and since that >>> involves some heavy lifting, it may seem more complicated at first >>> glance. >> >> I would like to better understand how Clojure's mitigation strategy >> is insufficient. Since Eli's document is all about the while macro, >> let's look at Clojure's while macro. > > I know very little about clojure, so I don't have a clue how this code > works. > [...] > Based on this, I tried to dig more with local > macros, and I found out that clojure doesn't have them. Whatever > clojure does, I think that prohibiting local macros is important. > [...]
Hello, yes, Clojure's mitigation strategy for avoiding hygiene problems has two components: The #-suffix syntax that acts as a clever shorthand for gensym and the `-quote syntax that employs reader magic to prefix every symbol read inside the syntax-quoted expression with a namespace. Gensym allows you to reliably avoid the problem that macro introduced identifiers might inadvertently shadow user defined identifiers. And the namespace prefixing makes the problem that user defined identifiers might inadvertently shadow identifiers used by macro generated code much less likely, but doesn't entirely prevent it. This is, in fact, precisely the same strategy employed by modern Common Lisp implementations. The namespace prefixing trick, however, would not easily be applicable to local macros. So if you want to break a macro that uses `(if ...) internally, you should use it in a context in which you rebind the identifier 'clojure.core/if', not simply 'if' ;-) Ciao, Thomas -- When C++ is your hammer, every problem looks like your thumb. _________________________________________________ For list-related administrative tasks: http://lists.racket-lang.org/listinfo/users