3
(define (orderedTriples n)
(set! i n)
(set! j n)
(set! k n)
(while (>= i 0)
   (while (>= j 0)
     (while (>= k 0)
       (printf "(~a, ~a, ~a)" i j k) 
       (set! k (- k 1))) 
     (set! j (- j 1))) 
  (set! i (- i 1))))

だから私の問題は...whileループをスキームで機能させる方法について混乱しています(私はこれに非常に慣れていないので、私がWAYオフの場合は構文を許してください)。問題を解決し、何を達成しようとしているのかを示すために、ここに入力しました。誰かが簡単な再帰の例やネストされた再帰を手伝ってくれませんか?

4

3 に答える 3

5

使用中の Scheme インタプリタに応じて、必要なループを実装する方法がいくつかあります。たとえば、Racket では、反復と内包を使用するのと同じくらい簡単です。

(define (orderedTriples n)
  (for* ([i (in-range n -1 -1)]
         [j (in-range n -1 -1)]
         [k (in-range n -1 -1)])
    (printf "(~a, ~a, ~a)" i j k)))

質問に示されているプログラミングのスタイル (それが機能していると仮定) は、Scheme では強く推奨されていません。set!ループにミューテーション (操作) を使用することは大したことではありません。C のような言語で問題を解決する方法ですが、特にScheme(および一般的なLisp)には、プログラムで反復を実装するための他の構成要素があり(たとえば、@TerjeDによって提供されるソリューションは、の使用を示していdoます)、そのような構成要素が存在しなくても、再帰的なソリューションまたは、高次の手順を使用したソリューションが優先されます。たとえば、ネストされたマッピングを標準の手順のみで使用する別の解決策を次に示します(ただし、printf非標準の は例外です)。

(define (range n)
  (if (negative? n)
      '()
      (cons n (range (- n 1)))))

(define (orderedTriples n)
  (for-each (lambda (i)
              (for-each (lambda (j)
                          (for-each (lambda (k)
                                      (printf "(~a, ~a, ~a)" i j k))
                                    (range n)))
                        (range n)))
            (range n)))
于 2013-02-03T23:24:57.320 に答える
2

次のように記述されたループを使用できますdo(関数の内部ループ用)。

(do ((k n (- k 1)))               ; variable, initialization, and updating form
   ((< k 0))                      ; stop condition, and optionally return value
  (printf "(~a, ~a, ~a)" i j k))  ; body forms

反復構造の詳細については、http://www.schemers.org/Documents/Standards/R5RS/HTML/r5rs-ZH-7.html#%_idx_138を参照してください。do

于 2013-02-03T23:03:10.957 に答える
1

必要に応じて、再帰を使用してこれを行うことができます。

(define (ordered-triples n)
  (let iloop ((i n))
    (unless (negative? i)
      (let jloop ((j n))
        (unless (negative? j)
          (let kloop ((k n))
            (unless (negative? k)
              (printf "~a ~a ~a\n" i j k)
              (kloop (sub1 k))))
          (jloop (sub1 j))))
      (iloop (sub1 i)))))

もちろんラケットのfor*ループの方が使いやすいです。

于 2013-02-04T10:01:47.937 に答える