我正在尝试使用函数来返回常见的lisp中的函数。但是,我遇到了一个我想解释的奇怪情况。
这就是我想要做的事情:
(defun makefun(x) ;1
(lambda (z)
(+ x z)))
((makefun 1) 2) ;2
这会导致非法的函数调用。但是,以下内容有效:
((lambda (z) (+ 1 z)) 2) ;3
(funcall (makefun 1) 2) ;4
为什么我不能像第一个例子那样使用makefun?我希望对2中的调用进行评估,这样就相当于第3行。
答案 0 :(得分:4)
Common Lisp有几个不同的namespaces,在function forms中,使用了运算符的functional value。您的lambda
示例有效,因为lambda forms是评估规则中的一个单独分支。你可以谷歌搜索" Common Lisp命名空间" " Lisp-1 vs. Lisp-2"有关详细信息,这里有很多问题和答案on SO,涵盖了这些主题。
但是,要回答您的具体问题,请使用funcall
(您还可以查看apply
):
(funcall (makefun 1) 2)
答案 1 :(得分:4)
如果在Stackoverflow上已经回答了类似的问题。这是重复的。需要找到它。
反正。
(defun makefun(x) ;1
(lambda (z)
(+ x z)))
((makefun 1) 2)
Common Lisp不允许在功能位置进行评估。它要求你在那里放置符号或实际的lambda表达式。
请记住:Common Lisp有一个单独的函数名称空间。 值命名空间是不同的。这里MAKEFUN
返回一个值,该值在函数名称空间中不可用。
调用函数只有两种语法:
(foo 1 2)
和
((lambda (a b) (list a b)) 1 2)
见CLHS (Conses as Forms)。这里我们有一个 Lambda表单。
添加写((some-function-returning-function) 1 2)
的功能会使Common Lisp中的函数调用更加混乱:
(foo 1 2)
将使用函数名称空间((some-function-returning-function) 1 2)
将使用值命名空间