3

SICPの演習3.8は、次のように説明されています。

セクション1.1.3で評価モデルを定義したとき、式を評価する最初のステップはその部分式を評価することであると述べました。ただし、部分式を評価する順序(たとえば、左から右または右から左)を指定したことはありません。割り当てを導入するとき、プロシージャへの引数が評価される順序は、結果に違いをもたらす可能性があります。+への引数が左から右に評価される場合は評価(+(f 0)(f 1))が0を返し、引数が右から左に評価される場合は1を返すように、単純なプロシージャfを定義します。

fそして、最初に電話をかけた場合、もう一度電話をかける(f x)と必ず戻るように手順を書きました。しかし、なぜそれが機能するのか正確にはわかりません。私が書いた手順は次のとおりです。xf

(define f
  (let ((s -1))
    (lambda (x)
      (if (= s -1)
          (begin (set! s x)
                 s)
           s))))
4

2 に答える 2

2

sプロシージャにのみ関連付けられ、呼び出し間でその値を保持する特別な変数と考えてください。SICPを実行しているので、SICPは、添付されている手順が存在する環境の一部であることを明確にする必要がありますf

初めてXで呼び出されると、に設定sされxて返されます。次回は、sがなくなったため、常に最初の呼び出しで保存された値であるを-1返します。sx

> (f 42)  ; s is -1, so 42 is saved into it and returned
42
> (f 10)  ; is is 42, so the 'else' branch of the 'if' is taken
          ; and s is returned without looking at x
42
> (f 20)
42
> 
于 2011-11-28T03:31:01.437 に答える
0

重要なことが1つあります。fの前後に角かっこを付けずに(define f .......)を使用すると、「body」が1回だけ評価される値を定義することになります。したがって、可変値は1回だけ初期化されます。また、結果のラムダ関数によってもキャプチャされます。ラムダ関数は、それを使って何でも実行できますが、定義の範囲内にあるため、他の場所からは表示されません。

于 2012-08-10T01:38:45.377 に答える