2013-04-10 9 views
5

私はFoxとGeeseタイプのゲームにAIを書いています。私の述語の1つは、次のようになります。Prolog findall/3:複数のバッグ

moveFox(+PrevState, -NextState, -PegList, +VisitedStates, -NewVisitedStates) 

これはゲームの状態を取り、キツネと一緒に動きます。結果の状態はNextStateで統一され、実際の移動はPegListで統一されます。すべてが期待どおりに機能します。

すべての移動のユーティリティスコアを計算中です。NextStateです。最高のユーティリティースコアを持つ状態を見つけるために、私はfindall/3を使用して、ユーティリティーのスコアを比較する前にリスト内のすべての状態を取得します。最高のユーティリティのスコアで、私が知っている最大の効用スコアNextState(だけでなく、リスト内の位置)を求めることにより

findall(NextState, moveFox(...), NextStatesList) 

。唯一の問題は、現在、私はNextStateに来て行われた動きを推測するために任意の述語、例えば:代わりに、このような述語を書く

getMove(+PrevState, +NextState, -PegList) 

を書いていない、があり、私はむしろfindall/3または同等のものを使用します。私の質問は、2つの異なる変数を2つの異なるリストに入れる方法があるかどうかです。 (それが働いているならば)私はこのように考えています:

findall([NextState, PegList], moveFox(...), [NextStatesList, MoveList]) 

私は二回findall/3を実行する(醜いオーバーヘッド)またはそのgetMove(+PrevState, +NextState, -PegList)述語を書くのいずれかにせずに、このような機能を実装してもらえますか?あなたのプロローグは、それがするのは簡単です、pairs_keys_values/3を持っていない場合は

答えて

3

この問題はペアのリストを構築する取り組み、その後、図書館のような要素を、分離することができます(pairsは)

... 
findall(NextState-PegList, moveFox(...), Pairs), 
pairs_keys_values(Pairs, NextStates, Pegs), 
... 

を行いますmaplistを使うか、再帰的述語を使って書きます。ここにマプリストの道があります:

pkv(K-V, K, V). 
pairs_keys_values(Pairs, Keys, Vals) :- 
    maplist(pkv, Pairs, Keys, Vals). 
+0

すごくお返事ありがとう!それは魅力のように働いた。 –