質問
私は SICP を (独力で) 取り組み始めたばかりです。これはクラス用ではありません)、私は演習 1.6 に数日間苦労していますが、まったく理解できません。これはアリッサが再定義したものです if
に関しては cond
, 、 そのようです:
(define (new-if predicate then-clause else-clause)
(cond (predicate then-clause)
(else else-clause))
彼女は、いくつかの単純なケースでそれを正常にテストし、それを使用して平方根プログラムを書き直します (これは問題なく動作しました)。 if
):
(define (sqrt-iter guess x)
(new-if (good-enough? guess x)
guess
(sqrt-iter (improve guess x)
x)))
次に質問は次のように尋ねます。「アリッサがこれを使って平方根を計算しようとするとどうなるでしょうか?説明してください。」 [必要に応じて、他の手順を再現させていただきます (good-enough?
, improve
, 、など)、お知らせください。]
さて、何が起こるかはわかっています:値を返すことはありません。これは、プログラムが無限に再帰することを意味します。なぜこんなことが起こるのか、私には説明できません。両者の間にどんな微妙な違いが存在しても、 if
そして new-if
私を避けています。あらゆるご協力に感謝いたします。
解決
new-if
機能です。関数が呼び出されると、スキームは、引数リストでない最初の事は何ですか?それが評価され、のすべてのの引数ます。
他のヒント
new-if
は、プロシージャで、SchemeはApplicativeの次評価(1.1.5)を使用するため、new-if
が実際に行われる前であっても、それはguess
と(sqrt-iter (improve guess x) x)
ある最初のすべての引数を評価する必要があります。あなたは、これは無限ループが発生したかで、後者の引数は新しいnew-if
プロシージャを呼び出す再帰、であることがわかります。
普通if
だけの道に沿って行く、最初の引数を評価する必要はないが、これはif
とnew-if
間の違いがあります。 :)
まず第一に、次のことを行う必要があります 違いを理解する 適用順序評価と通常順序の間。Lisp は適用順序を使用しますが、条件式は通常の関数とは異なります (SICP 章 1.1.6):
(if <predicate> <consequent> <alternative>)
if 式を評価するには、インタープリタはまず、
<predicate>
表現の一部。もし<predicate>
が true 値に評価されると、インタプリタは次の値を評価します。<consequent>
そしてその値を返します。それ以外の場合は、<alternative>
そしてその値を返します。
Ex1.6。新しい-の場合:
(define (new-if predicate then-clause else-clause)
(cond (predicate then-clause)
(else else-clause)))
「if文」が違い: -文があれば、述語から一つ一つを評価する - >後件 - >代替、
しかし、「新しい-場合は、」引数別名すべてのパラメータにMOMENTを評価するために持っているのと呼ばれる(意味開始!!で評価される「他の節」)、
、したがって、これは、これらのパラメータのいずれかが、反復ループに自分自身を呼び出す無限ループを生じさせる