SICP 読み (191) 4.2.2 遅延評価の解釈系
_a reformed C programmer_の意味的な部分を含め、最初は意図が全然分からんかったのですが、なんとなくこーゆー意味なのだろうか、という部分をメモ。
まず Cy さんが考える C のプログラム (というか手続きか) は以下??
int function(void){ int x; 手続き呼び出し1(); 手続き呼び出し2(); 手続き呼び出し3(); /* 上記手続きで x の状態は変化していると見る */ return x; }
最後に戻すのは変数だからね、という意味での
((last-exp? exps) (eval (first-exp exps) env))
なのかなぁ、と。
ただ気になるのは、全部 actual-value すりゃいいんじゃね??、というソレ。
(define (eval-sequence exps env) (cond ((last-exp? exps) (actual-value (first-exp exps) env)) (else (actual-value (first-exp exps) env) (eval-sequence (rest-exps exps) env))))
ってなっていた場合、どのような不具合が起こり得るんだろうか。てか、何故に eval-sequence は eval のままで OK って事にしたんだろうか。
つづき
eval-sequence が使われる場面としては
- compound-procedure を apply する時
- cond 式の cond-actions は begin 式に変換される
- begin 式は eval される時に eval-sequence される
くらいか。問題になってるソレは一番てっぺん。for-each なソレだと一番下ですか。でも何故に
(define (for-each proc items) (if (null? items) 'done (begin (proc (car items)) (for-each proc (cdr items)))))
だと OK かとゆーと、begin 式の中身な手続き自体は delay されていないから、でビンゴかなぁ。ちなみに上記手続きが eval された時、delay されるのは proc と items になる。逆に
(define (p2 x) (define (p e) e x) (p (set! x (cons x '(2)))))
の場合、e に束縛される式全体が delay されてるんで、という事ッスか。これ、ダウトだったら泣くなぁ。ビンゴ前提で続けますが eval-sequence は
(define (eval-sequence exps env) (cond ((last-exp? exps) (actual-value (first-exp exps) env)) (else (actual-value (first-exp exps) env) (eval-sequence (rest-exps exps) env))))
で問題ないはず (断言
中身見りゃ分かりますが、actual-value では渡された式を eval して force-it しているだけです。force-it では thunk 又は evaluated-thunk でなければもらった式をそのまま戻しているだけなんで、というのが根拠なんですが ...
てーか、こればっかりは試験してみないと何とも言えません。ってどんな試験すりゃええんだろうか。