【发布时间】:2015-08-10 02:53:51
【问题描述】:
我正在学习SICP,ex1.20给出如下代码:
(define (gcd a b)
(if (= b 0)
a
(gcd b (remainder a b))))
问题询问我们分别以应用顺序和正常顺序运行(gcd 206 40) 时调用余数的次数。我可以弄清楚剩余部分按应用顺序被调用了 4 次,但我不明白为什么在正常顺序中它变成 18 次。在我看来,首先调用(gcd 40 (remainder 206 40)),接下来我们需要计算(remainder 206 40),也就是6,如果我们想知道我们去哪个分支,然后(remainder 40 6),以此类推,结果是也是4倍。但答案给出了以下过程:
(gcd 206 40)
(if (= 40 0) ...)
(gcd 40 (remainder 206 40))
(if (= (remainder 206 40) 0) ...)
(if (= 6 0) ...)
(gcd (remainder 206 40) (remainder 40 (remainder 206 40)))
(if (= (remainder 40 (remainder 206 40)) 0) ...)
(if (= 4 0) ...)
(gcd (remainder 40 (remainder 206 40)) (remainder (remainder 206 40) (remainder 40 (remainder 206 40))))
(if (= (remainder (remainder 206 40) (remainder 40 (remainder 206 40))) 0) ...)
(if (= 2 0) ...)
(gcd (remainder (remainder 206 40) (remainder 40 (remainder 206 40))) (remainder (remainder 40 (remainder 206 40)) (remainder (remainder 206 40) (remainder 40 (remainder 206 40)))))
(if (= (remainder (remainder 40 (remainder 206 40)) (remainder (remainder 206 40) (remainder 40 (remainder 206 40)))) 0) ...)
(if (= 0 0) ...)
(remainder (remainder 206 40) (remainder 40 (remainder 206 40)))
所以总共是 18 次。 我认为这两个答案之间的主要区别在于,我认为一旦计算了余数,就不需要再计算它了,但答案似乎每次都计算它。这是编译器的问题吗?是不是太没效率了?
【问题讨论】: