从prolog谓词获取多个答案
假设我有一个谓词,它有时会给我多个输出。像这样-从prolog谓词获取多个答案,prolog,prolog-setof,Prolog,Prolog Setof,假设我有一个谓词,它有时会给我多个输出。像这样- foo(Number, Out) :- Number < 10, Out = less_than_ten. foo(Number, Out) :- Number > 0, Out = more_than_zero. 然后我可以输入一个分号,让prolog回溯并寻找另一个解决方案- ?- foo(5, Out). Out = less_than_ten ; Out = more_than_zero. 因此,如果我在另一个谓词中执行此
foo(Number, Out) :- Number < 10, Out = less_than_ten.
foo(Number, Out) :- Number > 0, Out = more_than_zero.
然后我可以输入一个分号,让prolog回溯并寻找另一个解决方案-
?- foo(5, Out).
Out = less_than_ten ;
Out = more_than_zero.
因此,如果我在另一个谓词中执行此谓词,那么如何获得Out的所有有效值,给定的数字=5?如果您只考虑整数,那么可以选择使用CLP(FD)。那么您的谓词foo可能如下所示:
:- use_module(library(clpfd)).
foo(Nums) :-
Nums ins 1..9. % the numbers in the list Nums are 0 < X < 10
如果要使用它生成该范围内的整数列表,必须确保Nums
是一个列表,以避免实例化错误。您可以通过在查询中为目标长度/2添加前缀来实现这一点:
?- length(Nums,_), foo(Nums).
Nums = [] ? ; % <- no number
Nums = [_A], % <- one number
_A in 1..9 ? ;
Nums = [_A,_B], % <- two numbers
_A in 1..9,
_B in 1..9 ? ;
Nums = [_A,_B,_C], % <- three numbers
_A in 1..9,
_B in 1..9,
_C in 1..9 ?
.
.
.
刚刚找到了回答这个问题的谓词。Prolog有一个内置谓词
bagof(Template,Goal,Bag)
,它将Goal
谓词的Template
参数与Bag
参数统一起来(不确定这是正确的Prolog行话!)。因此,在问题的示例中,使用bagof(Out,foo(5,Out),Outputs)。
,这将把Out
的解决方案列表与Outputs
统一起来。在SWI prolog中运行查询:
4 ?- bagof(Out, foo(5, Out), Outputs).
Outputs = [less_than_ten, more_than_zero].
?- length(Nums,_), foo(Nums).
Nums = [] ? ; % <- no number
Nums = [_A], % <- one number
_A in 1..9 ? ;
Nums = [_A,_B], % <- two numbers
_A in 1..9,
_B in 1..9 ? ;
Nums = [_A,_B,_C], % <- three numbers
_A in 1..9,
_B in 1..9,
_C in 1..9 ?
.
.
.
?- length(Nums,_), foo(Nums), label(Nums).
Nums = [] ? ;
Nums = [1] ? ;
Nums = [2] ? ;
Nums = [3] ? ;
.
.
.
Nums = [1,1] ? ;
Nums = [1,2] ? ;
Nums = [1,3] ? ;
.
.
.
Nums = [9,9] ? ;
Nums = [1,1,1] ? ;
Nums = [1,1,2] ? ;
.
.
.
4 ?- bagof(Out, foo(5, Out), Outputs).
Outputs = [less_than_ten, more_than_zero].