2

2 つのベクトル/リストを取り、最初のベクトル/リストをフィルターとして使用する述語を作成しようとしています。例えば:

?- L1=[0,3,0,5,0,0,0,0],L2=[1,2,3,4,5,6,7,8],filter(L1,L2,1).
   L1 = [0, 3, 0, 5, 0, 0, 0, 0],
   L2 = [1, 2, 3, 4, 5, 6, 7, 8] .

それは私が得ているものですがtruefalseL2 が32 番目の要素5として、4 番目の要素としてなどを持っている場合、 0s は無視されます。それが「フィルター」条件です。入力からわかっていることは、L1 と L2 は常に長さ = 8 であり、L1 だけが0s を持つということです。

私のコードは次のとおりです。

filter(_,_,9).
filter([Y|T],V2,Row):-
    Y=:=0,
    NewRow is Row + 1,
    filter([Y|T],V2,NewRow).

filter([Y|T],V2,Row):-
    Y=\=0,
    nth(Row,[Y|T],X1),
    nth(Row,V2,X2),
    X1=:=X2,
    NewRow is Row + 1,
    filter([Y|T],V2,NewRow).


nth(1,[X|_],X).  
nth(N,[_|T],R):- M is N-1, nth(M,T,R).

関数を実行するより良い方法があることは知っています。たとえば、最初の要素の最初の要素を 2 番目の n 番目と比較し、再帰を使用して最初の要素の先頭を削除しますが、またはtrueを取得しない理由を知りたいだけです。false任意の「戻り値」。

誰かが私を助けることができますか?

新しいコード:

filter([],R,_,R).
filter([Y|T],V2,Row,R):-
Y=:=0,
NewRow is Row + 1,
filter(T,V2,NewRow,R).

filter([Y|T],V2,Row,R):-
Y=\=0,
nth(Row,V2,X2),
Y=:=X2,
NewRow is Row + 1,
filter(T,V2,NewRow,R).

予想される動作の例:

permutation([1,2,3,4,5,6,7,8],X),filter([1,2,3,4,0,0,0,0],X,1,R).
X = R, R = [1, 2, 3, 4, 5, 6, 7, 8] ;
X = R, R = [1, 2, 3, 4, 5, 6, 8, 7] ;
X = R, R = [1, 2, 3, 4, 5, 7, 6, 8] ;
X = R, R = [1, 2, 3, 4, 5, 7, 8, 6] .

これで、1、2、3、4 で始まるすべての順列を取得できます。誰かが同じことを達成するためのより良い方法を知っている場合は、共有してください。しかし、私はすでに必要なものを手に入れました =)。

4

2 に答える 2

3

maplist/3 の完璧なタスクのようです

filter(L1, L2, _) :-
  maplist(skip_or_match, L1, L2).

skip_or_match(E1, E2) :- E1 == 0 ; E1 == E2.

収量

?- permutation([1,2,3,4,5,6,7,8],X),filter([1,2,3,4,0,0,0,0],X,_).
X = [1, 2, 3, 4, 5, 6, 7, 8] ;
X = [1, 2, 3, 4, 5, 6, 8, 7] ;
X = [1, 2, 3, 4, 5, 7, 6, 8] ;
X = [1, 2, 3, 4, 5, 7, 8, 6] ;
...

Prolog 機能を使用すると、より便利に実行できます。つまり、 an を使用してanonymus variableを表現できdon't careます。

次に、filter/N は maplist の単純なアプリケーションです。

?- permutation([1,2,3,4,5,6,7,8],X),maplist(=,[1,2,3,4,_,_,_,_],X).
X = [1, 2, 3, 4, 5, 6, 7, 8] ;
X = [1, 2, 3, 4, 5, 6, 8, 7] ;
X = [1, 2, 3, 4, 5, 7, 6, 8] ;
X = [1, 2, 3, 4, 5, 7, 8, 6] ;
...
于 2013-05-11T06:00:45.210 に答える