获取子句的其余部分作为列表并创建列表列表

时间:2019-10-06 20:39:04

标签: prolog

假设我有一些子句,其中两个是以下子句:

const

如何编写名为

的规则
has_basket('Sarah', 'bigBasket','apple','grape').
has_basket('Sarah', 'bigBasket','orange','berry').

这将以以下形式给我S人拥有的所有篮子的清单? 例如

all_baskets(S,L).

会给我们:

all_baskets('Sarah',L).

2 个答案:

答案 0 :(得分:2)

每当您考虑Prolog编程问题时,都需要澄清对您来说很重要的方面。

  1. 请考虑列表中两个元素的顺序。是因为它们是按字母升序排列的,还是因为运气好?

  2. 您对all_baskets('Nemo', L)有什么期望?应该失败还是回答L = []

  3. 您对all_baskets(P, [])有什么期望?

如果您说1个字母,2个失败和3个失败,那么setof/3是最好的选择。

has_basket('Sarah',  bigBasket, apple, grape).
has_basket('Sarah',  bigBasket, orange, berry).
has_basket('Bernie', bigBasket, orange, apple).  % another fact

all_baskets(P, L) :-
   setof([A, B, C], has_basket(P, A, B, C), L).

?- all_baskets(P, []).
false.

?- all_baskets('Nemo', L).
false.

?- all_baskets(P, L).
   P = 'Bernie',
   L = [[bigBasket, orange, apple]]
;
   P = 'Sarah',
   L = [[bigBasket, apple, grape], [bigBasket, orange, berry]].

答案 1 :(得分:1)

我们可以利用findall/3 predicate [swi-doc]

all_baskets(S,L) :-
    findall([A, B, C], has_basket(S, A, B, C), L).

[A, B, C]是列表中项目的“模板”,has_basket(S, A, B, C)是需要填写的“目标”,而L是结果列表。