SICP自引用流求值疑问:整数流计算步骤是否正确?
SICP无限整数流的求值过程验证
先给出示例代码:
; 工具过程 (define (add-streams s1 s2) ; 返回两个流对应元素相加后的新流 (cond ((empty-stream? s1) s2) ; 若任一流为空,返回非空流 ((empty-stream? s2) s1) (else (cons-stream (+ (head s1) (head s2)) ; 新流的头部是两个流头部的和 (add-streams (tail s1) (tail s2))))) ; 新流的尾部是两个流尾部递归相加的结果 (define ones (cons-stream 1 ; 全为1的无限流 ones)) (define integers (cons-stream 1 ; 从1开始的递增无限整数流 (add-streams integers ones)))
我需要验证(head (tail (tail integers)))的求值过程,尤其是第二步中(tail integers)是否等价于(add-streams (cons 2 (delay ...)) (cons 1 (delay ...)))。
逐步推导求值过程
首先明确:cons-stream是特殊形式,头部立即求值,尾部延迟求值(不会立即计算,直到调用tail时才触发)。
第一步:计算(tail integers)
integers的定义是(cons-stream 1 (add-streams integers ones)),调用tail会触发尾部延迟表达式(add-streams integers ones)的求值:
s1是integers,头部为1,尾部是延迟的(add-streams integers ones)s2是ones,头部为1,尾部是延迟的ones- 进入
add-streams的else分支,生成新流:
也就是(cons-stream (+ 1 1) (add-streams (tail integers) (tail ones)))(cons-stream 2 (add-streams (tail integers) ones))(因为(tail ones)就是ones)。
此时(tail integers)的结果就是这个流,头部为2,对应第二个整数。
第二步:计算(tail (tail integers))
这一步是取上面得到的流的尾部,触发延迟表达式(add-streams (tail integers) ones)的求值:
- 此时
s1就是第一步得到的(tail integers),也就是(cons-stream 2 (add-streams (tail integers) ones)) s2还是ones,即(cons-stream 1 (delay ones))- 进入
add-streams的else分支,生成新流:
也就是(cons-stream (+ 2 1) (add-streams (tail (tail integers)) (tail ones)))(cons-stream 3 (add-streams (tail (tail integers)) ones))。
此时(head (tail (tail integers)))就是3,对应第三个整数。
疑问验证
你提到的“第二步中的(tail integers)调用还原为(add-streams (cons 2 (delay ...)) (cons 1 (delay ...)))”是正确的:
- 第二步求值
(add-streams (tail integers) ones)时,(tail integers)已经是第一步求值完成的流(cons-stream 2 (delay ...)) ones始终是(cons-stream 1 (delay ones))- 所以此时
add-streams的两个参数确实是这两个流,你的还原符合实际求值逻辑。
内容的提问来源于stack exchange,提问作者user51462
相关产品推荐
相关产品推荐

