Use findall
to accomplish this:
P2(ARGUMENTS, LIST) :- findall(X, P1(ARGUMENTS, X), LIST).
This is related to the bagof
function mentioned in the question linked to by Anders Lindahl. There is a good explanation on the relationship between the two functions (and a third function setof
) here:
To illustrate the differences consider
a little example:
listing(p).
p(1,3,5).
p(2,4,1).
p(3,5,2).
p(4,3,1).
p(5,2,4).
Try the following goals. (The answer
displays have been modified to save
space.)
?- bagof(Z,p(X,Y,Z),Bag).
Z = _G182 X = 1 Y = 3 Bag = [5] ;
Z = _G182 X = 2 Y = 4 Bag = [1] ;
Z = _G182 X = 3 Y = 5 Bag = [2] ;
Z = _G182 X = 4 Y = 3 Bag = [1] ;
Z = _G182 X = 5 Y = 2 Bag = [4] ;
No
?- findall(Z,p(X,Y,Z),Bag).
Z = _G182 X = _G180 Y = _G181 Bag = [5, 1, 2, 1, 4] ;
No
?- bagof(Z,X^Y^p(X,Y,Z),Bag).
Z = _G182 X = _G180 Y = _G181 Bag = [5, 1, 2, 1, 4] ;
No
?- setof(Z,X^Y^p(X,Y,Z),Bag).
Z = _G182 X = _G180 Y = _G181 Bag = [1, 2, 4, 5] ;
No
The predicates bagof
and setof
yield
collections for individual bindings of
the free variables in the goal. setof
yields a sorted version of the
collection without duplicates. To
avoid binding variables, use an
existential quantifier expression. For
example the goal
bagof(Z,X^Y^p(X,Y,Z),Bag)
asks for
"the Bag of Z
's such that there exists
an X
and there exists a Y
such that
p(X,Y,Z)
". findall
acts like bagof
with all free variables automatically
existentially quantified. In addition
findall
returns an empty list []
there
is no goal satisfaction, whereas bagof
fails.