0

私は小さなPrologプログラムを書いています。それは次のように何かをすることが期待されています:

?-input([allan,is,a,name]).
 true.
?-input([Is,allan,a,name]).
 true.

そしてここに私のコードがあります:

% Simple answering agent

input(Text) :-
phrase(sentence(S), Text), 
perform(S).

sentence(statement(S)) --> statement(S).

sentence(query(Q))     --> query(Q).

statement(Statement) --> 
    [Thing, 'is', 'a', Category],
    { Statement =.. [Category, Thing]}.

query(Query) --> 
   ['Is', Thing, 'a', Category],
   { Query =.. [Category, Thing]}.

perform(statement(S)) :- asserta(S).

perform(query(Q))     :- Q.

パーツは正常に動作してinput([allan,is,a,name]).いるように見えますが、クエリパーツに問題があり、入力するinput([Is,allan,a,name]).と出力されます。

Is = 'Is'

誰かが私のためにこの問題を見てくれませんか、ありがとう。

4

1 に答える 1

2

さて、問題はそれIsが変数であり、したがってプロローグがそれを(で'Is')インスタンス化することです。リストのすべてのメンバーがアトムであることを確認することをお勧めしますが、簡単に修正するには、次のようにすることができます。

query(Query) --> 
[_, Thing, 'a', Category],
{ Query =.. [Category, Thing]}.

このように、Isインスタンス化されることはなく、プロローグはただ真と言うでしょう。唯一の問題は、ステートメントがクエリとして解釈される可能性があることです。

9 ?- input([allan, is, a, name]).
true ;                                   
false.                                   

10 ?- input([is, is, a, name]).       
true .                                   

11 ?- input([allan, is, a, name]).       
true ;                                   
true.

これはいくつかのカットで修正できます(またはそれが許容できる場合は-Thingとは異なるはずだと言っています)'is'

編集:より一般的な解決策の場合:解析する文の種類と、ユーザーが行う可能性のある妥協点によって異なります。たとえば、プロローグアトムである単語を与えるように彼に依頼することが可能かもしれません。大文字で始まる単語が要求された場合、彼はを使用する必要があります''。それ以外の場合は、文字列/アトム('Is allan a name'または"Is allan a name")で指定する方が適切です。個々のアトムに簡単に分離できます。atomic_list_concat/3を使用します。あなたはwhat is allanまだ何か特別​​なことをする必要はありません。残りは4語でしたが、3語の文なので、すぐに分けることができます。

于 2012-10-14T18:10:31.800 に答える