方案括号是非常特殊的。他们的意思是apply
:
(define (test arg) arg)
((test +) 4 5) ; ==> 9
JavaScript中的一样:
const plus = (a, b) => a+b; // Needed since + is not a function in JS
const test = arg => arg
test(plus)(4,5) // ==> 9
在你的代码有:
((display (/ (+ (* b -1) (sqrt det)) (* 2 a)))
(display (/ (- (* b -1) (sqrt det)) (* 2 a))))
不幸的是,在操作位置返回#<undef>
表达。实际上,根据规范,它可以返回任何东西,因为它在规范中未定义。 IB您的具体实现,虽然它不是一个功能,所以它是这样的:
((test 'symbol) 4 5); ==> Error: symbol is not a function
正如你前面看到的具有test
一个电话没工作较早所以在操作员位置表情是完全有效的代码,几乎不可能在编译时推理,但是在运行时它将变得很明显,当应用程序获得非函数时不可能继续。
现在有一些宏使用括号来表示应用程序以外的东西,而这些只是必须知道或阅读的文档。一个例子是cond
(cond ((= 3 5) #t)
(else #f))
; ==> #f
如果你从来没有见过cond
很容易承担((= 3 5) #t)
是看它,它不应该因为(= 3 5)
工作的表达,当然,也不会计算为一个函数对象但之前布尔值。然而,cond
中的每个术语评估它的car
,然后评估其余部分中的每个元素,如果它碰巧是一个真正的值。
,以便做更多的表达式并返回最后一个表达式的值使用begin
:
(begin 1 2 3)
; ==> 3
这里评估1
和2
显然是死代码,因为它没有做任何事情。因此,其继承使用begin
意味着副作用,其中返回值不重要,但副作用是。我不认为你的功能真的需要副作用:
(define (roots a b c)
(define det
(- (* b b) (* 4 a c)))
(cond ((> det 0)
(list (/ (+ (* b -1) (sqrt det)) (* 2 a))
(/ (- (* b -1) (sqrt det)) (* 2 a))))
((= det 0)
(list (/ (* b -1) (* 2 a))))
((< det 0)
(list (/ (+ (* b -1) (make-rectangular 0 (sqrt (* det -1)))) (* 2 a))
(/ (- (* b -1) (make-rectangular 0 (sqrt (* det -1)))) (* 2 a))))))
(roots -1 4 -4) ; ==> (2 -2)
(roots 1 0 -4) ; ==> (2)
(roots 4 0 4) ; ==> (0+1i 0-1i)
谢谢。是的,我打算在if的主体中添加一个开始,现在我明白为什么显示会导致错误。它现在有效。 –