我是Prolog的新手。这是我的事实。
part_cost(部分,供应商)
part_cost(top_tube ,cinelli).
part_cost(top_tube ,columbus).
part_cost(down_tube ,columbus).
part_cost(head_tube ,cinelli).
part_cost(head_tube ,columbus).
part_cost(seat_mast ,cinelli).
part_cost(seat_mast ,columbus).
我想找一家供应各种零件的供应商,实际上是哥伦布。
我不知道如何用Prolog语言说“全部”。
感谢任何帮助。
更新
谢谢@Ankur和@Sergey Dymchenko。你的清单方法激励着我!我可以写规则:
supplyAllParts(Supplier, []):-true.
supplyAllParts(Supplier, [Part|PartRest]) :-
part_cost(Part, Supplier, _, _),
supplyAllParts(Supplier, PartRest).
并通过
调用它?- supplyAllParts(S,[top_tube, down_tube, head_tube, seat_mast]).
S = columbus.
现在Prolog可以从事实中动态查找零件清单([top_tube,down_tube,head_tube,seat_mast])而不是我手动提供它吗?
答案 0 :(得分:1)
首先,您可能需要手动定义“所有部分”的概念,因为可能存在某种“bottom_super_gravitsapa”,没有人拥有:
% store in sorted order, to compare with setof results later
sort([top_tube, down_tube, head_tube, seat_mast], AllParts)
要获取每个供应商的所有零件清单,我们可以使用setof/3
:
?- setof(Part, part_cost(Part, Supplier), Parts).
setof(Part, part_cost(Part, Supplier), Parts).
Supplier = cinelli
Parts = [head_tube,seat_mast,top_tube] ?;
Supplier = columbus
Parts = [down_tube,head_tube,seat_mast,top_tube]
yes
现在只需添加一个条件,即特定供应商的零件清单和AllParts是相同的:
Parts == AllParts
如果您不想手动定义AllParts并假设每个可能的部件都有供应商,您可以使用另一个setof
从主setof
之前的事实中获取AllParts。 / p>
答案 1 :(得分:1)
all
在任何一种语言中都是一个大词,它意味着变化如此......在地球上,在Prolog我们有findall / 3家族,它输出一个列表我们指示从成功的查询中提取的所有模式。然后进一步处理输出列表...但对于您的情况,库(aggregate)更方便:
supplies_all(Supplier) :-
aggregate(max(N,S), count_part_cost(S,N), max(_, Supplier)).
count_part_cost(S,N) :-
aggregate(count, P^part_cost(P,S), N).
我使用了服务谓词count_part_cost / 2,只是为了保持主要的清晰... 如果您尝试“内联”它们,请注意变量的使用。研究变量量化,直到你对它感到满意为止。
编辑正如谢尔盖所说,我的代码不正确。以下是我更合适的定义:
supplies_all(Supplier) :-
setof(P, S^part_cost(P,S), Ps),
setof(P, part_cost(P,Supplier), Ps).
我认为它突出了我上面推荐的关于研究变量量化的建议......
编辑另一种可能的定义,成本更低,但有多余的多重解决方案(好吧,我们已经设定了...)
supplies_all(Supplier) :-
% peek any Supplier from catalog
part_cost(_,Supplier),
% check it has all parts available
forall(part_cost(P,_), part_cost(P,Supplier)).
答案 2 :(得分:1)
supplies([],_).
supplies([H|T],S) :- part_cost(H,S), supplies(T,S).
| ?- setof(P,S^part_cost(P,S),R), supplies(R,Supplier).
R = [down_tube,head_tube,seat_mast,top_tube]
Supplier = columbus