1

編集:シングルトン変数を見つけました。Prolog は、データ バンクの大文字化された単語が好きではありません。また、コードにいくつかの大幅な変更を加えました。

edit:edit : 再帰呼び出しがないことに気付きました。ダープ

Haskell を使用した関数型プログラミングの経験はありますが、Prolog にはかなり慣れていません。

関数にステートメントを真にするすべての可能な値を出力させようとすると問題が発生しますが。過去数時間調べてきたので、論理エラーではないと思いますが、間違っている可能性があります。

この問題では、車の所有履歴を作成しようとしています。

-- 私はある人が車を所有していることを知っています。

これらの事実を知っているので、車、所有者、およびこの再帰の基本ケースとして機能するディーラーの別の変数を作成するデータバンクを設定しました。

car(prius).
car(bmw).

owner(meg).
owner(nora).
dealer(d).

boughtFrom(meg,nora).
boughtFrom(nora,d).

私は、メグがディーラーから購入したノラから購入したことを立証しました。ディーラーから購入すると、これがベースケースのエンドポイントであるため、私が計画している再帰は停止します。したがって、ロジックは次のようになります。

ownCar(X,Y) :- boughtFrom(X,d), car(Y).
ownCar(X,Y) :- ownCar(boughtFrom(_,prevowner(X)), car(Y)).

あなたがディーラーである場合、または前の所有者から車を購入した場合は、車の所有者になることができます。ディーラーまたは別の前の所有者から購入した場合は、その前の所有者が所有者です。などなど したがって、停止するのは、その人がディーラーから車を購入したときだけです。

4

1 に答える 1

0

明らかな関係が欠落しているため、データベースが不完全だと思います。

たとえば、このルールはすべてのownCar(X,Y) :- boughtFrom(X,d), car(Y).Y に当てはまります。つまり、ディーラーから購入した人は誰でも各車を「所有」します。

表現も不正確です。売り手は、車を売った後は所有者であってはなりません。

とにかく、Prolog では結合(これはリレーショナル データ モデルです) を記述してから、推移的なプロパティのクロージャを取得します。

ownCar(X, Y) :- owner(O), boughtFrom(X, O), ownCar(O, Y).

Prolog では、無限ループにつながる可能性があるため、左再帰を避ける必要があることに注意してください。結合の順序が重要です。

編集

履歴を (リストとして) 取得するには、述語に引数を追加するか、「出力」をリストに変更する必要があります。次のようなことができます

ownCar(X, Y, [X]) :- boughtFrom(X,d), car(Y).
ownCar(X, Y, [X|L]) :- owner(O), boughtFrom(X, O), ownCar(O, Y, L).

注: 従来、Prolog では、最後の引数の位置に「出力」引数を配置します。

于 2013-03-17T19:19:12.177 に答える