假设我有一个特殊的var:
(defvar x 20)
然后我做以下事情:
(let ((x 1)) (eval '(+ x 1))
评估为2。
根据CLHS,eval“评估当前动态环境和零词汇环境中的形式”。所以,我希望得到21而不是2。
我错过了什么吗?
现在,如果我没有符号y的动态绑定,则进行评估
(let ((y 1)) (eval '(+ y 1))
我得到条件:“变量Y是未绑定的”,这是有道理的,因为y没有动态绑定。
注意:我使用的是SBCL 1.0.57
提前感谢您的帮助!
在你的例子中 x
是 special
这意味着它受到约束 动态环境
y
是 不 特别的,所以它受到约束 词汇环境
所以在第一次的时候 eval
环境可以这样表示:
dynamic environment: { x : 1 } -> { x : 20, ...other global variables... } -> nil
lexical environment: nil
符号 x
很特别 eval
仰望;查询 x
在里面 当前 动态
环境和发现 x = 1
假设它与最后一个例子在同一个lisp中运行,第二个例子就是环境 eval
看起来像这样:
dynamic environment: { x : 20, ...other global variables... } -> nil
lexical environment: { y : 1 } -> nil
符号 y
是 不 特别的 eval
仰望;查询 y
在里面 空值
词汇环境 - 不 当前的词汇环境 - 一无所获。
当你意识到通常编译lisp和词法时,这是有道理的
环境可以优化到简单 mov
某些情况下的说明。
在你的例子中 x
是 special
这意味着它受到约束 动态环境
y
是 不 特别的,所以它受到约束 词汇环境
所以在第一次的时候 eval
环境可以这样表示:
dynamic environment: { x : 1 } -> { x : 20, ...other global variables... } -> nil
lexical environment: nil
符号 x
很特别 eval
仰望;查询 x
在里面 当前 动态
环境和发现 x = 1
假设它与最后一个例子在同一个lisp中运行,第二个例子就是环境 eval
看起来像这样:
dynamic environment: { x : 20, ...other global variables... } -> nil
lexical environment: { y : 1 } -> nil
符号 y
是 不 特别的 eval
仰望;查询 y
在里面 空值
词汇环境 - 不 当前的词汇环境 - 一无所获。
当你意识到通常编译lisp和词法时,这是有道理的
环境可以优化到简单 mov
某些情况下的说明。
DEFVAR
声明其变量特殊。在全球范围内,无处不在。你也不能轻易删除它。
这也是你永远不应该使用常见名称的原因 x
, i
, list
作为变量名称 DEFVAR
。确保使用 *x*
, *i*
和 *list*
代替。否则,具有这些通用名称的所有变量(甚至是本地变量)都被声明为特殊