コードではループを使用していません。すべての出現を取得するには、何とか反復する必要があります。
これは、通常、再帰によってnamed let
で行われます。各反復中に、インデックス変数i
、結果リストr
、および残りの入力リストL
があり、各反復ステップの間に小さくなります。
例のif
節を簡略化することができます。
リストの最初の要素の値を見つけた場合は、インデックスを増分し、現在のインデックスを結果リストに追加し、残りの入力リストを続行します。
一致するものがない場合は、インデックスをインクリメントしますが、インデックスを結果リストに追加して残りの入力リストも続行しないでください。
L
がnullの場合、入力リストの最後に達しました。その場合、結果リストを返します。 cons
は先頭に追加されるので、結果リストを逆にする必要があります。
(define positions
(lambda (A L)
(let loop ((i 0)
(r '())
(L L))
(if (null? L)
(reverse r)
(if (eq? (car L) A)
(loop (+ i 1) (cons i r) (cdr L))
(loop (+ i 1) r (cdr L)))))))
ループの引数にif句を入れることで、loopコマンドを2回入力することを避けることができます。
(define positions
(lambda (A L)
(let loop ((i 0)
(r '())
(L L))
(if (null? L)
(reverse r)
(loop (+ i 1)
(if (eq? (car L) A)
(cons i r)
r)
(cdr L))))))
BTW:SchemeはCまたはJavaとして静的に型指定されていません。これは、-1でCで行われるように、予約された変数値のエラーをエンコードする必要がないことを意味します。 Schemeでは、偽#f
または空のリスト'()
のいずれかを返すか、(error "Sorry")
でエラーを返します。
ヒント:式を正しく整列させるエディタを使用してみてください。これはSchemeの生活を単純化します。例えば、[Emacs](http://emacs.stackexchange.com/)を試してみてください。 – ceving
特に、 'emacs'と' paredit'です。 –