为什么这会导致无限循环[SICP]?

时间:2020-07-28 11:28:35

标签: functional-programming scheme sicp

我正在处理SICP的问题。我不确定为什么这个函数会导致一个无限的while循环。有人可以说明一下吗?我相信可能会有更好的方法来编写此循环,但是我对函数式编程还是陌生的,并且仍然试图将自己的头放在这样的编写循环上。

(define (search-for-primes a b)
        (if (> a b) (display " Done"))
        ((timed-prime-test a) (search-for-primes (+ a 1) b)))

程序将继续为此输入打印“ Done”(搜索素数2 10),这没有任何意义。 “定时素数测试”是一种检查输入是否为素数的功能。或不。这就是我的想法:该程序会不断调用自身直到a = 11,此时它将退出。但是,即使对于前9次迭代(a = 2到a = 10),我也看不到“ timed-prime-test”函数的输出,这向我表明该控件甚至没有到达第二行,但是如何到达第二行。函数调用是无限次发生的吗?

编辑:我再次在书中查看'if'的语法,我注意到两件事:a)'alternative'是我的代码在if块之外,这是错误的。我已解决此问题,但程序输出为a =10。b)脚注说它应该只包含单个表达式。我的程序的这种行为是否与b)有关?如果是,在这种情况下程序如何执行?

2 个答案:

答案 0 :(得分:4)

如果正确设置代码格式,答案将立即清楚。 这就是为什么正确设置代码格式很重要的原因。这是格式更好的定义:

(define (search-for-primes a b)
  (if (> a b)
      (display " Done"))
  ((timed-prime-test a) (search-for-primes (+ a 1) b)))

所以(search-for-primes 1 1)

  • 测试1是否大于1 ...否;
  • 然后开始评估((timed-prime-test a) (search-for-primes (+ a 1) b)),以执行以下操作:
    • 以某种顺序评估(timed-prime-test 1)(search-for-primes 2 1),这至少意味着评估(search-for-primes 1 1),其中:
      • 测试2是否大于1 ...
        • 因此它显示“完成”;
      • 然后开始评估...哎呀。

现在应该清楚问题出在哪里。

答案 1 :(得分:0)

((timed-prime-test a) (search-for-primes (+ a 1) b))

(search-for-primes (+ a 1) b)的递归调用的当前延续为((timed-prime-test a) _),但它从未到达_,因为您从未填充其值,即_的值是bottom type。所以((timed-prime-test a) _)的值也是一个底数。

但是search-for-primes的值就是((timed-prime-test a) _)的值。因此它没有任何价值。