(sicp53)問題4.14,4.15
4.14
make-lambdaで取り付けられたtag'procedureを基底の処理系が評価する手段をもって無いためerrorになる。
以下詳しく
(記憶が確かなら)define、set!を使わない箇所では、副作用を利用していない。
なので、置き換えで評価される様子を表すことができる。
driver-loopを起動して、そこで"(map (lambda (x) (* x x)) '(1 2 3))"という式が渡されると、評価器は以下のように動作する。
mapが組み込み手続きの場合
(eval (map (lambda (x) (* x x)) '(1 2 3)) global-environment) ;以下渡された式は<exp>と表記する ;global-environmentは<ENV>で表す ;;aplication?でtrueになる (@apply (eval (operator <exp>) <ENV>) (list-of-values (operands <exp>) <ENV>))) ;;左から評価される ;operator=car (@apply (eval 'map <ENV>) (list-of-values (operands exp) <ENV>)) ;;evalでmapはvariable?でtrueになる ;<map>はmapの手続き (@apply (primitive <map>) (list-of-values (operands exp) <ENV>)) ;operands=cdr ;;list-of-valuesの引数が左から展開されてく (@apply (primitive <map>) (list-of-values ((lambda (x) (* x x)) '(1 2 3)))) ;list-of-valuesが展開されてく (@apply (primitive <map>) (cons (eval (lambda (x) (* x x)) <ENV>) (list-of-values ('(1 2 3))))) ;;lambda?でtrue以下に変わる (@apply (primitive <map>) (cons ('procedure (x) (* x x) <ENV>) (list-of-values ('(1 3 3))))) ;;quoted?でtrueで最後にnilになって終了 (@apply (primitive <map>) (('procedure (x) (* x x) <ENV>) '(1 2 3))) ;;@applyの手続きが適用される ;*ここでprimitive-procedure?でtrueになるので以下の用に置換される (apply-primitive-procedure (primitive <map>) (('procedure (x) (* x x)) <ENV>) '(1 2 3)) ;;apply-primitive-procedureの処理が進む (apply (primitive-implementation (primitive <map>) ('procedure (x) (* x x) <ENV>) '(1 2 3))) ;このapplyはgaucheのapply ;;最終的には以下のような処理が呼ばれる (map (procedure (x) (* x x) <ENV>) '(1 2 3)) ;;procedureなんてもの(gaucheは)知らない>error *** ERROR: invalid application: ((procedure (x) ((* x x)) (((car primitive #<s...
4.15
仮にhalts?が定義できるなら、(try try)の動作はどうなるか?という問題
halts?が定義すると仮定してみる。
(define (run-forever) (run-forever)) (define (try p) (if (halts? p p) (run-forever) 'halted)) ;;(halts? f x) ::= (f x)が停止するかどうか
halts?で渡した手続きが停止するのかどうか分かるとする。
halts?がnil以外の値を返すなら必ず手続きが停止するとする。
(try try)とした場合
(if (halts? try try))
という式に置き換えられる(多分、halts?とかは副作用を使っていない)
halts?がnil以外の値を返す場合、
(halts?は実行が停止すると判断した)しかし、後の(run-forever)から停止しない処理を実行する
halts?がnilを返した場合
(halts?は実効が停止しないと判断した)しかし、後の'haltedから返り値を返すことがわかる。
こんな感じで上の仮定とは矛盾してしまうので、halts?は定義できない。