我正在学习Clojure中的宏,并希望编写“cond”宏。
我遇到了将参数解析为(条件)(参数)和编写递归宏的问题。
请帮帮我。
答案 0 :(得分:4)
我写这篇文章是为了说明这个过程。这段代码有很多bug但是这个过程会让你尽快找到有趣的部分:) 写出对你的宏的调用以及你想要转换成的调用(这一步不是可选的;)
(my-cond (even? 4) 42 (odd? 4 24))
(if (even? 4) 42 (if (odd? 4) 24)))
为最简单的案例编写一个模板,然后将其提供给(macroexpand-1 ...)并旋转直到匹配
(defmacro my-cond [test result] `(if ~test ~result nil))
(macroexpand-1 '(my-cond (even? 4) 42) ==> (if (even? 4) 42)
现在让它更通用
(defmacro my-cond [& cases]
`(if (if ~(first cases) ~(second cases) ~(my-cond (drop 2 cases))
然后在macroexpand-1中播放,然后在macroexpand中播放(带有“-1”)以确保它完全扩展到正确的情况
然后通过并清理那些有奇数条款的角落等......
然后查看core.clj,看看你有多接近。