如何知道函数是否评估其参数?

时间:2014-07-28 15:19:50

标签: lisp common-lisp evaluation clisp

如何知道函数是否评估其参数?

Setq似乎不会评估其论点,而是

Break 15 [16]> (setq j (kjl klj))
*** - EVAL: undefined function KJL

那么评估何时完成?

condand似乎也不会评估他们的论点,但......

Break 18 [19]> (cond ((eql nil nil) (write "lkj")))
"lkj"
"lkj"
Break 18 [19]> (cond ((eql nil (not nil)) (write "lkj"))
NIL
上面示例中的

cond必须评估(eql nil nil)以确定它是否真实,不是吗?

1 个答案:

答案 0 :(得分:7)

理论:Form Evaluation

功能

运行时在将参数传递给function之前评估参数(例如eql)。

例如,当您编写(eql a 1)时,函数eql会获取变量a的值以及文本1的值。

运行时评估macros的参数(例如condand)。 宏将它们的参数转换为代码,然后由运行时进行评估。

例如,当你写cond ((eql nil nil) (write "lkj")))时,它会扩展为:

> (macroexpand '(cond ((eql nil nil) (write "lkj"))))
(IF (EQL NIL NIL)
    (PROGN (WRITE "lkj"))
    NIL)

然后根据其规范评估if表单作为特殊运算符。

当然,您不想真正阅读cond的宏展开以了解它的作用 - 您阅读了文档。但是,您确实使用macroexpand来调试自己的宏。

特别经营者

运行时处理special operators(例如setq),以及特别,即行为对每个特殊操作符都是特殊的。

例如,当您编写(setq a (! 4))时,运行时评估a,但它会评估(! 4),它会发现!对函数进行fbound,因此它会计算4evaluates to itself),然后使用参数!调用4的函数绑定,并指定返回值( 24}变量a

顺序

实际上,正如@Paulo在评论中提到的那样,首先检查符号是否为特殊运算符(因为实现可以将宏实现为特殊运算符和vv);它不能同时是一个宏和一个函数(但你可以使用compiler macros)。这不属于这个问题的范围......

练习:使用CLHS

在Emacs中编辑代码,加载clhs.el,然后查看您感兴趣的符号的文档。 该会立即说明符号的定义。