SICP 练习 1.11

问题描述

我无法获得执行结果。

我认为它无限期地重复了。

我通过在计数上加 1 并重复它来创建一个结构。

我做错了什么?

   #lang sicp
   (define (fi n)
    (f-iter 0 3 n))
 
  (define (f-iter sum count n)
    (cond ((= count (+ n 1)) sum)
          ((< count 3) count)
          (+ (f-iter sum (- count 1) n)
             (* 2 (f-iter sum (- count 2) n))
             (* 3 (f-iter sum (- count 3) n))
             sum))
          (+ count 1)
          (f-iter sum count n))

解决方法

您需要做的第一件事是正确缩进代码:

(define (f-iter sum count n)
  (cond ((= count (+ n 1)) sum)
        ((< count 3) count)
        (+ (f-iter sum (- count 1) n)
           (* 2 (f-iter sum (- count 2) n))
           (* 3 (f-iter sum (- count 3) n))
           sum))
  (+ count 1)
  (f-iter sum count n))

让我们用注释来注释代码:

(define (f-iter sum count n)
  (cond ((= count (+ n 1)) sum)
        ((< count 3) count)
        (+ (f-iter sum (- count 1) n)       ; the syntax of COND expects
                                            ; a list with a condition as
                                            ; the first element.
                                            ; here the first element is the
                                            ; function +,which is always true.
                                            ; as such it makes no sense.

           (* 2 (f-iter sum (- count 2) n))
           (* 3 (f-iter sum (- count 3) n))
           sum))                            ; here the result of COND is not
                                            ; used anymore. It is not returned from
                                            ; f-iter.

  (+ count 1)                               ; this result is never used.

  (f-iter sum count n))                     ; this calls the same function with the
                                            ; same arguments. Thus
                                            ; f-iter calls itself
                                            ; indefinitely at this point.
,

最后的代码总结了我在问题下方的评论。

对于大于等于 3 的任何 n 值,您需要函数在 n 的三个以上值处的值。对于 n = 3,您需要 f(2)、f(1) 和 f(0)。对于 f(4),您需要 f(3)、f(2)、f(1)。您需要从先前的计算中获得三个较旧的值才能进行新的计算。因此,在您的迭代函数中,您需要保留三个参数来存储上述 3 个值,一个参数用于存储 n 的值,以及一个用于跟踪进度的计数器参数。

(define (funcn n) (func-iter 2 1 0 n 2))

(define (func-iter p1 p2 p3 n count) ; p1 and p2 exchange places with
                                     ; p2 and p3 respectively on every iteration
  (cond ((= n 0) 0)
        ((= n 1) 1)
        ((= n count) p1) ; p1 stores the cumulative sum to be returned
                         ; when 'count' is equal to n
        (else (func-iter (+ p1 (* p2 2) (* p3 3)) p1 p2 n (+ count 1)))
  )
)