11.3.78 findall/[3,4] [ISO]

Synopsis

findall(+Template, +Generator, -List)

findall(+Template, +Generator, -List, +Remainder)

List is the list of all the instances of Template for which the goal Generator succeeds, appended to Remainder. Remainder defaults to the empty list.

Arguments

Template
term
:Generator
callable, must be nonvar

A goal to be proved as if by call/1.

List
list of term
Remainder
list of term

Description

A special case of bagof/3, where all free variables in the generator are taken to be existentially quantified, as if by means of the ‘^’ operator. Contrary to bagof/3 and setof/3, if there are no instances of Template such that Generator succeeds, then List = Remainder.

Because findall/[3,4] avoids the relatively expensive variable analysis done by bagof/3, using findall/[3,4] where appropriate rather than bagof/3 can be considerably more efficient.

Please note: If the instances being gathered contain attributed variables (see lib-atts) or suspended goals (see ref-sem-sec), those variables are replaced by brand new variables, without attributes, in List. To retain the attributes, you can use copy_term/3 (see ref-lte-cpt).

Backtracking

bagof/3 can succeed nondeterminately, generating alternative values for Set corresponding to different instantiations of the free variables of Generator.

Exceptions

Call errors (see ref-sem-exc).

Examples

To illustrate the differences among findall/3, setof/3, and bagof/3:

     | ?- [user].
     | foo(1,2).
     | foo(1,2).
     | foo(2,3).
     |
     % user compiled in module user, 0.100 sec 352 bytes
     
     yes
     | ?- bagof(X, foo(X,Y), L).
     
     Y = 2,
     L = [1,1] ? ;
     
     Y = 3,
     L = [2] ? ;
     
     no
     | ?- bagof(X, Y^foo(X,Y), L).
     
     L = [1,1,2] ? ;
     
     no
     | ?- findall(X, foo(X,Y), L).
     
     L = [1,1,2] ? ;
     
     no
     | ?- findall(X, foo(X,Y), L, S).
     
     L = [1,1,2|S] ? ;
     
     no
     | ?- setof(X, foo(X,Y), L).
     
     X = _3342,
     Y = 2,
     L = [1] ;
     
     X = _3342,
     Y = 3,
     L = [2] ;
     
     no

Comments

findall/3 is part of the ISO Prolog standard; findall/4 is not.

See Also

bagof/3, setof/3, ^/2, ref-all.


Send feedback on this subject.