There seems to be some difference between short backquote and long backquote.
(let ((x 123))
(dolist (res (list `(a `(b ,x))
`(a (backquote (b ,x)))
(backquote (a (backquote (b ,x))))
(backquote (a `(b ,x)))))
(print res)))
Output:
(a (\` (b (\, x))))
(a (backquote (b 123)))
(a (backquote (b 123)))
(a (\` (b (\, x))))
Why does it behave differently as to x? Not even sure which two of the four results are supposed to be the surprising results.
By default, Common Lisp is lexically scoped, that is, every variable is lexically scoped except for special variables. By default, Emacs Lisp files are dynamically scoped, that is, every variable is dynamically scoped. The my-test. el is a lexically scoped file because of the first line.
Emacs Lisp is a dialect of the Lisp programming language used as a scripting language by Emacs (a text editor family most commonly associated with GNU Emacs and XEmacs). It is used for implementing most of the editing functionality built into Emacs, the remainder being written in C, as is the Lisp interpreter.
Gnu emacs is written almost entirely in Common Lisp! Unfortunately, this version of Common Lisp is so incomplete that it won't be sufficient for programming in our class. Instead, you can run and use lisp within emacs.
Emacs Lisp supports multiple programming styles or paradigms, including functional and object-oriented. Emacs Lisp is not a purely functional programming language since side effects are common. Instead, Emacs Lisp is considered an early functional flavored language.
I'm not sure if it is a bug or a feature, mainly because I'm not sure if a elisp programmer is allowed/good practice to use the backquote
function, or it is just a convenient way of defining the function. The correct output is the first (and fourth) output. Looking at the code for backquote
(in backquote.el
) it is clear that any backquote
inside either a ` or backquote
is not properly expanded. The relevant code for this is:
((eq (car s) backquote-backquote-symbol)
(backquote-delay-process s (1+ level)))
where backquote-backquote-symbol
is defined before as '\` (quote-backslash-backtick). There are several ways of treating this error, but the line could be then:
((or (eq (car s) backquote-backquote-symbol)
(eq (car s) 'backquote))
(backquote-delay-process s (1+ level)))
(or using any other variable for specifying the backquote unaliased symbol).
EDIT: Looking at it more closely, there is another place where you have to add that test too, but this includes reporting a patch. I'll see how do I do it. With that change:
ELISP> (macroexpand-all `(a (backquote (b ,x))))
(a
(list 'b x))
ELISP> (macroexpand-all `(a `(b ,x)))
(a
(list 'b x))
If you love us? You can donate to us via Paypal or buy me a coffee so we can maintain and grow! Thank you!
Donate Us With