Prolog: Filtering a list?
SWI-Prolog offers exclude/3
and other such meta-predicates. Your original problem can be coded like this:
are_identical(X, Y) :-
X == Y.
filterList(A, In, Out) :-
exclude(are_identical(A), In, Out).
Usage example:
?- filterList(A, [A, B, A, C, D, A], Out).
Out = [B, C, D].
If you are searching for higher-order functions in Prolog, you should definetly consult Naish (1995), a very good resource on this.
His definition of filter/3
is the following (he uses difference-list notation, therefore escapes having to define filter/4
):
filter(_,[],[]).
filter(P, A0-As0, As) :-
(
call(P, A0) -> As = A0-As1
;
As = As1
)
, filter(P, As0, As1).
I you have questions about this predicate, please ask me in the comment. Reading the paper is also highly recommended, it also definess map
, foldr
and compose
! Note that many of the limitations he mentions (like, for example a missing call/3
or a higher-order apply
do not apply anymore. SWI-Prolog has the =..
operator, which addresses all of his concerns and makes arbitrary n-order logic possible.