web-dev-qa-db-ja.com

スキームコンソール印刷

Schemeから始めたところです。コンソールでの印刷に問題があります。簡単なリスト印刷の例:

 (define factorial
   (lambda (n)
     (cond 
       ((= 0 n) 1)
       (#t (* n (factorial (- n 1)))))))

関数が呼び出されるたびにnを出力したいと思います。同じ関数内ではそれができないと思ったのですか?印刷するためだけに別の関数を呼び出す必要がありますか?

19
ercliou

Schemeでの印刷は、display(場合によってはnewline)を呼び出すことで機能します。他の何か(関数(またはSchemeの場合はfunction-ish)の言語では、呼び出された関数の副作用に対してのみ意味がある)の前後に順次呼び出したいので、通常はbeginを使用する必要があります。 、引数を順番に評価し、最後の部分式の値を返します。ただし、lambdaには、このようなbegin- expressionが暗黙的に含まれています。

したがって、あなたの場合、それは次のようになります:

 (lambda (n)
   (display n) (newline)
   (cond [...]))

2つの備考:

  1. (define (factorial n) [...])の省略形として(define factorial (lambda (n) [...]))を使用できます。
  2. factorialを実装する方法は tail call-optimization を禁止するため、プログラムはnの値が大きい場合にかなりのスタックスペースを使用します。ただし、アキュムレータを使用して最適化可能な形式に書き換えることは可能です。

nを1回だけ出力する場合は、ユーザーが関数を呼び出すときに、実際に次のようなラッパーを作成する必要があります。

 (define (factorial n)
   (display n) (newline)
   (inner-factorial n))

次に、関数の名前をinner-factorialに変更します。

34
fnl