我在运行SICP(计算机程序的结构和解释)第3.5.4节(流和延迟评估)中的示例代码时遇到问题;可在此处找到SICP部分:http://mitpress.mit.edu/sicp/full-text/book/book-Z-H-24.html#%_sec_3.5.4。
我正在使用DrRacket版本5.2.1,使用Neil Van Dyke的SICP支持语言( SICP PLaneT 1.17 )进行设置,可在此处找到:http://www.neilvandyke.org/racket-sicp/#%28part._installation%29。< / p>
如下所示,代码使用了流。如上所述设置环境,DrRacket已经提供了cons-stream
,force
和delay
程序。但stream-car
和stream-cdr
不可用;所以,我必须定义它们。在下面的代码中,我还定义了一些通用流函数:stream-map
,stream-ref
,add-streams
和scale-stream
。
我正在努力完成的整个代码如下。它包括使用积分过程(solve
)以数字方式(integral
)求解一阶微分方程的过程,该过程使用延迟参数(delayed-integrand
);这些程序来自第3.5.4节。
(define (stream-car stream) (car stream))
(define (stream-cdr stream) (force (cdr stream)))
(define (stream-map proc . argstreams)
(if (stream-null? (car argstreams))
the-empty-stream
(cons-stream
(apply proc (map stream-car argstreams))
(apply stream-map
(cons proc (map stream-cdr argstreams))))))
(define (stream-ref s n)
(if (= n 0)
(stream-car s)
(stream-ref (stream-cdr s) (- n 1))))
(define (add-streams s1 s2)
(stream-map + s1 s2))
(define (scale-stream stream factor)
(stream-map (lambda (x) (* x factor)) stream))
(define (integral delayed-integrand initial-value dt)
(define int
(cons-stream initial-value
(let ((integrand (force delayed-integrand)))
(add-streams (scale-stream integrand dt)
int))))
int)
(define (solve f y0 dt)
(define y (integral (delay dy) y0 dt))
(define dy (stream-map f y))
y)
当我将上面的定义放在DrRacket中并单击Run时,不会发生错误。但是,当我尝试在交互窗口中执行以下行时发生错误:
(stream-ref (solve (lambda (y) y) 1 0.001) 1000)
错误消息是:
mcar: expects argument of type <mutable-pair>; given #<undefined>
发生此错误时,DrRacket会突出显示过程stream-car
定义的正文,如下图所示:
<小时/>
导致此错误的原因是什么?我已经在之前的示例(stream-car
,stream-cdr
,stream-map
,add-streams
和scale-stream
)中使用了上述流程序,并且它们有效。当我在integral
程序之外使用它时,solve
程序也有效;例如,如果我定义(define ones (cons-stream 1 ones))
然后我定义(define s (integral (delay ones) 1 1))
然后执行(stream-ref s 1000)
,它会正确地给出输出1001
。
答案 0 :(得分:4)
您报告的错误相当奇怪,我无法看到正在使用mcar
的位置 - 或者此类问题的可变状态。尝试这个设置,它适用于我而不使用Neil Van Dyke的支持语言:
#lang racket
(define the-empty-stream '())
(define (stream-null? stream)
(null? stream))
(define-syntax cons-stream
(syntax-rules ()
((cons-stream head tail)
(cons head (delay tail)))))
(define (stream-car stream)
(car stream))
(define (stream-cdr stream)
(force (cdr stream)))
; ... the rest is the same as in your question