In clojure, how to define defmacro in terms of itself?

I am looking at a defmacro source that uses "let" in its definition:

(def ^{:doc "Like defn, but the resulting function name is declared as a macro and will be used as a macro by the compiler when it is called." :arglists '([name doc-string? attr-map? [params*] body] [name doc-string? attr-map? ([params*] body)+ attr-map?]) :added "1.0"} defmacro (fn [&form &env name & args] (let [prefix (loop [p (list name) args args] 

However, let is defined as the macro itself:

 (defmacro let "binding => binding-form init-expr Evaluates the exprs in a lexical context in which the symbols in the binding-forms are bound to their respective init-exprs or parts therein." {:added "1.0", :special-form true, :forms '[(let [bindings*] exprs*)]} [bindings & body] (assert-args (vector? bindings) "a vector for its binding" (even? (count bindings)) "an even number of forms in binding vector") `(let* ~(destructure bindings) ~@body )) 

Can someone explain how this works, since I cannot figure out how to define "defmacro" in terms of things for which "defmacro" is already defined. (if that makes sense :)

+7
source share
2 answers
Recusrive macros

work great and are found in many places both in the core of the clojure language, and in other programs. macros are simply functions that return S expressions , so they can be recursive as they can function. In the case of let in your example, this is really the quotation mark let* , which is another function (its fine to have * in the function name), so although the recursive macros are fine, this is not an example of them

+5
source

This is possible because before defmacro is defined in core.clj, there is already a let definition at that location (which is subsequently redefined). Macros are just normal functions, and they have a meta data key :macro with a value of true , so during compilation the compiler can distinguish a macro (which is executed at compile time) using a function without this meta key can not distinguish a macro and a function, because the macro itself is a function that processes S-expressions.

+8
source

All Articles