Prolog 过滤自定义目标失败的所有元素的列表

问题描述 投票:0回答:3

我正在尝试编写一个谓词

filter(List, PredName, Result)
,过滤其目标
List
失败的所有元素的
PredName
,并随后返回
Result
列表。谓词
PredName/1
应在调用过程
filter/3
时定义,例如可以是:

test(N) :- N >= 0

然后可以像下面这样进行查询:

?- filter([-6,7,-1,0], test, L)
L = [7, 0];
no
prolog meta-predicate
3个回答
3
投票

如果您使用 SWI-Prolog,您可以使用

“apply”库中的 
exclude 谓词


1
投票

我确信存在一个内置操作可以执行此操作...但本质上您只是尝试对传递谓词的列表成员执行 findall 操作。 尝试这个过滤器的实现。 运行 findall 的第二个参数,直到所有结果都用尽并且 M 的所有值都收集到 Result 中。

filter(List,PredName,Result) :-
  findall(M, ( member(M, List), call(PredName,M)), Result).

-1
投票

一种方法是使用递归和

call/2
谓词

filter([],_,[]).
filter([H|T], PredName, [H|S]) :-  call(PredName,H),filter(T,PredName,S),!.
filter([H|T], PredName, S) :- filter(T,PredName,S).

另一种方法是,您可以使用

call/2
(univ) 运算符,而不是使用
=..

filter([],_,[]).
filter2([H|T], PredName, [H|S]) :-  Goal =.. [PredName,H],Goal,filter(T,PredName,S),!.
filter([H|T], PredName, S) :- filter(T,PredName,S).

=..
运算符采用包含谓词名称及其参数的列表,并返回新创建的术语。例如:

?-X =.. [f,a,b].
X = f(a, b).
© www.soinside.com 2019 - 2024. All rights reserved.