I’ve written an ebook about Programming Language Concepts Show me!
The code presented here is available on github .
The obvious parts
You’ll be aware of these if you’ve ever bothered writing macros:
- Both prevent evaluation of the subsequent expression:
`(1 2 3) ;; => (1 2 3)
'(1 2 3) ;; => (1 2 3)
- Backtick allows you to unquote parts of the expression:
(def x 3)
`(1 2 ~x) ;; => (1 2 3)
'(1 2 ~x) ;; => (1 2 (clojure.core/unquote x))
As you can see, quote does not interpret the tilde character (which is just a reader macro for clojure.core/unquote).
- …or even additionally splice a sequence:
(def y (list 3 4))
`(1 2 ~@y) ;; => (1 2 3 4)
'(1 2 ~@y) ;; => (1 2 (clojure.core/unquote-splicing y))
Same thing here – quote does not do anything with the “~@” reader macro, as it is just an alias for clojure.core/unquote-splicing.
The subtle part
- However, quote and backtick show different behavior in how they handle namespace resolution for the symbols they quote:
(def z 111)
`(1 2 z) ;; => (1 2 user/z)
'(1 2 z) ;; => (1 2 z)
So why is this relevant?
Well, consider the following code. The essence of this is that we have a namespace macro-ns in which macros get defined. Those macros are being used in another namespace (user here):
(def z 222)
(defmacro m-quote 
(defmacro m-backtick 
;; Now, we'll want to use these macros in the "user" namespace:
(def z 111)
(macroexpand-1 '(macro-ns/m-quote)) ;; => z
(macroexpand-1 '(macro-ns/m-backtick)) ;; => macro-ns/z
(macro-ns/m-quote) ;; => 111
(macro-ns/m-backtick) ;; => 222
So obviously it does matter whether you use quote or backtick in a macro, even if you don’t intend to use any unquoting within. As you can see above, m-quote refers to user/z, while m-backtick results in an expansion that uses macro-ns/z.