2013-06-30 49 views
8

短反引用和長反引用似乎有一些區別。嵌套反引用和'in emacs lisp

(let ((x 123)) 
    (dolist (res (list `(a `(b ,x)) 
        `(a (backquote (b ,x))) 
        (backquote (a (backquote (b ,x)))) 
        (backquote (a `(b ,x))))) 
    (print res))) 

輸出:

(a (\` (b (\, x)))) 

(a (backquote (b 123))) 

(a (backquote (b 123))) 

(a (\` (b (\, x)))) 

爲什麼會表現不同,以X?甚至不知道四項結果中的哪兩項應該是令人驚訝的結果。

+0

那些實際上是反襯 –

+0

我認爲這是'backquote.el'中的一個錯誤。看到我下面的評論。 –

回答

3

我不確定它是一個錯誤還是一個功能,主要是因爲我不確定是否允許elisp程序員使用backquote函數/好的練習,或者它只是一種方便的方式來定義功能。正確的輸出是第一個(和第四個)輸出。查看backquote的代碼(在backquote.el中),很明顯,在backquotebackquote中的任何backquote未正確擴展。此相關的代碼是:

((eq (car s) backquote-backquote-symbol) 
     (backquote-delay-process s (1+ level))) 

其中backquote-backquote-symbol之前定義爲「\'(引-反斜槓反引號)。有幾種處理這種錯誤的方法,但是該行可以是:

((or (eq (car s) backquote-backquote-symbol) 
     (eq (car s) 'backquote)) 
     (backquote-delay-process s (1+ level))) 

(或使用任何其他變量來指定反引用非混淆符號)。

編輯:更仔細地看,還有另一個地方,你必須添加該測試,但這包括報告一個補丁。我會看看我該怎麼做。隨着這種變化:

ELISP> (macroexpand-all `(a (backquote (b ,x)))) 
(a 
(list 'b x)) 
ELISP> (macroexpand-all `(a `(b ,x))) 
(a 
(list 'b x))