Prolog:找到两个列表的交集?

时间:2015-03-02 23:43:57

标签: prolog

让我们说我有Prolog事实,例如:

fact1(x, [y1, y2, y3, y4]).

fact2(z1, [s, t, u, **y3**).
fact2(z2, [o, p, **y1**, q, r]).
fact2(z3, [**y1**, m, **y3**, n]).
fact2(z4, [j, k, **y4**, l]).
fact2(z5, [**y2**, d, e, f, g, h,  i]).
fact2(z6, [a, b, c, **y4**]).

并且,我想要一个查询,以便我得到所有' z'谁与x有关。

因此,此查询应输出z1,z2,z3,z4,z5,z6,因为它们都包含元素y1,y2,y3和/或y4,因为它们与第一个Prolog事实中的x相关。

以下代码输出事实2的所有z&#39关系:

fact2(_,X).

以下代码输出x< fact1:

的关系
fact1(x,X).

因此,我认为我需要使用以下代码获取两组的交集,但它不起作用。

xyz(X):-
  intersection(fact2(_,X),fact2(x,X),X).

这不起作用,有人能引导我朝着正确的方向前进吗?

通过查询,我需要得到的是:z1,z2,z3,z4,z5,z6,因为它们都包含y1,y2,y3和/或y4,因为这些都与x int他的第一个事实。

如果您需要澄清,请告诉我。谢谢。

2 个答案:

答案 0 :(得分:0)

您必须在不同的变量中将fact2和fact1上的每个术语实例化,否则您将强制实例匹配相同。此外,在事实" fact2"上丢失星号,并在元素y3之后关闭第一个事实" fact2"中的扣环。 如果你想保留星号,请将它们用单引号括起来。

fact1(x, [y1, y2, y3, y4]).

fact2(z1, [s, t, u, '**y3**']).
fact2(z2, [o, p, y1, q, r]).
fact2(z3, [y1, m, y3, n]).
fact2(z4, [j, k, y4, l]).
fact2(z5, [y2, d, e, f, g, h,  i]).
fact2(z6, [a, b, c, y4]).
xyz(Z):-  fact2(Z,X),fact1(_,Y), intersection(X,Y,I), I\=[].

然后试着问:

?- xyz(X)

或者如果你想在单个列表中得到所有答案L:

?- setof(Z, xyz(Z), L).

答案 1 :(得分:0)

此代码段

xyz(L):-
    fact1(x, L1),
    setof(K, L2^I^(fact2(K, L2), intersection(L1,L2,I), I \= []), L).

产量

?- xyz(L).
L = [z1, z2, z3, z4, z5, z6].