2

こんにちは、最初の n 個の数値の合計を計算するのを手伝ってくれる人はいますか? たとえば、n=4 => sum = 10 です。

    predicates
  sum(integer,integer)
clauses

  sum(0,0).
   sum(N,R):-
        N1=N-1,
        sum(N1,R1),
        R=R1+N.

これは機能しますが、別の実装が必要です。どうすればこれを違うものにすることができるのか、私には考えがありません。助けてください

4

5 に答える 5

6

@mbratchが言ったこと。

あなたが計算しているのは三角数です。宿題が三角数に関するものであり、再帰的思考の学習に関するものではない場合、次のように単純に計算できます。

triangular_number(N,R) :- R is N * (N+1) / 2 .

再帰的思考を学んでいる可能性が高い場合は、これを試してください。

 sum(N,R) :-    % to compute the triangular number n,
   sum(N,1,0,R) % - invoke the worker predicate with its counter and accumulator properly seeded
   .

 sum(0,_,R,R).     % when the count gets decremented to zero, we're done. Unify the accumulator with the result.
 sum(C,X,T,R) :-   % otherwise,
   C > 0 ,         % - assuming the count is greater than zero
   T1 is T+X ,     % - increment the accumulator
   X1 is X+1 ,     % - increment the current number
   C1 is C-1 ,     % - decrement the count
   sum(C1,X1,T1,R) % - recurse down
   .               % Easy!

追加するために編集:

または、カウント ダウン アプローチを好む場合は、次のようにします。

 sum(N,R) :- sum(N,0,R).

 sum(0,R,R).       % when the count gets decremented to zero, we're done. Unify the accumulator with the result.
 sum(N,T,R) :-     % otherwise,
   N > 0 ,         % - assuming the count is greater than zero
   T1 is T+N ,     % - increment the accumulator
   N1 is N-1 ,     % - decrement the count
   sum(N1,T1,R)    % - recurse down
   .               % Easy!

これらは両方とも末尾再帰です。つまり、プロローグ コンパイラはそれらを反復に変換できます (詳細については、Google の「末尾再帰の最適化」を参照してください)。

アキュムレータを削除したい場合は、次のようにする必要があります。

sum(0,0).
sum(N,R) :-
  N > 0 ,
  N1 is N-1 ,
  sum(N1,R1) ,
  R is R1+N
  .

少し単純ですが、再帰ごとに別のスタック フレームが消費されます。N の値が十分に大きい場合、実行はスタック オーバーフローで失敗します。

于 2014-01-09T23:04:36.217 に答える
3
sum(N, Sum) :-
    Sum is (N + 1) * N / 2 .
于 2014-01-10T10:10:59.030 に答える
2

コードについてすでに多くのアドバイスをいただいているので、スニペットを挿入させてください (トピックから少し外れます)。

カウント、より一般的に言えば、集約は、他のリレーショナル宣言型言語 (SQL を参照) と比較した場合、Prolog が輝かない領域です。しかし、いくつかのベンダー固有のライブラリはそれをより快適にします:

?- aggregate(sum(N),between(1,4,N),S).
S = 10.
于 2014-01-10T13:57:18.150 に答える