2013-03-04 43 views
1

望着方式有些特殊形式展开:用户可以定义特殊形式的宏吗?

(macroexpand '(String. "foo")) 
(macroexpand '('a)) 
;; etc 

...并意识到他们是用宏实现让我好奇的是,什么是用户定义的宏的语法形式的限制。到目前为止,我所有的宏在语法形式上都与函数相似。不过,这将是可能的,例如,定义,像下面?:

(macroexpand '(myprintln-foo)) 
;;=> (println "foo") 
(macroexpand '(myprintln-zoo)) 
;;=> (println "zoo") 

回答

1

,如果我理解正确的话,你试图写一个reader macro和简单的答案是“不,是不可能的'(或者至少不支持)。

看看this article及其评论

3

的限制是宏必须有一个有效的名称,并返回一个表达式的宏。例如,它不能在调用命名空间之前将某些东西附加到表达式的末尾,也不能将两个表达式按顺序插入到调用名称空间中(而不是通过将它包装在一个do中来将其表达式)编写一个宏定义很多宏:

(defmacro make-printers [& names] 
    `(do [email protected](for [name names] 
      `(defmacro ~(symbol (str "myprintln-" name)) [] 
       (println ~(str name)))))) 

user> (make-printers foo bar) 
#'user/myprintln-bar 
user> (myprintln-foo) 

foo 
nil 
user> (myprintln-bar) 
bar 
nil 

宏只返回一个s表达式函数表达式可以是任何东西,只要它是一个有效的s表达式(功能ARG ARG ...) 。宏的名字必须与要调用的宏完全匹配,所以宏的名字不能是宏的一部分。你可以用新的extensible reader功能来接近你的问题,虽然它不是你所想的需要

PS:这是值得指出的是,这个例子违反宏观俱乐部的第一条规则是“unhygenic”

+0

请看更新。我的意思是,是否有可能以某种方式影响角色的标记和对构成令牌的认识。否则,在“String”的宏展开的情况下。我不清楚什么是扩展的宏名称(我不认为宏“字符串”是硬编码定义的) – 2013-03-04 18:53:53

+0

这使得它更清晰,谢谢。我会编辑我的回复 – 2013-03-04 19:12:59

相关问题