Functional programming 从术语/目标列表中查找成功次数

Functional programming 从术语/目标列表中查找成功次数,functional-programming,logic-programming,mercury,functional-logic-progr,Functional Programming,Logic Programming,Mercury,Functional Logic Progr,我已经编写了以下谓词精确/2,如果列表L中的数字精确N等于1,则该谓词将成功: :- pred exactly(int, list(int)). :- mode exactly(in, in) is semidet. :- mode exactly(out, in) is det. exactly(N, L) :- length(filter(pred(X::in) is semidet :- (X = 1), L), N). 例如,调用(X[1,0,0,1,0,1])将X绑定到3 我

我已经编写了以下谓词
精确/2
,如果列表
L
中的数字精确
N
等于1,则该谓词将成功:

:- pred exactly(int, list(int)).
:- mode exactly(in, in) is semidet.
:- mode exactly(out, in) is det.
exactly(N, L) :-
    length(filter(pred(X::in) is semidet :- (X = 1), L), N).
例如,调用
(X[1,0,0,1,0,1])
X
绑定到
3

我想创建一些类似的东西,但对于谓词:我想编写一个谓词,如果列表中的
L
目标确实成功,那么该谓词就会成功


例如,调用
应该精确地(X,[true,false,member(1[1,2,3]),member(0[1,2,3])
绑定
X
2

实际上,这是可以做到的,如下代码所示:

:- module exactly.

:- interface.
:- import_module io.

:- pred main(io::di, io::uo) is det.

:- implementation.

:- import_module int.
:- import_module list.

main(!IO) :-
    Test1 = list_member(1, [1, 2, 3]),
    Test2 = list_member(0, [1, 2, 3]),
    Tests = [Test1, Test2],
    exactly(N, Tests),
    io.write_line(N, !IO).

:- pred exactly(int::out, list((pred))::in(list_skel((pred) is semidet)))
    is det.

exactly(0, []).
exactly(N, [Test | Tests]) :-
    exactly(NTail, Tests),
    ( if Test then
        N = NTail + 1
    else
        N = NTail
    ).

:- pred list_member(T::in, list(T)::in) is semidet.

list_member(E, L) :-
    list.member(E, L).
谓词列表_成员告诉编译器 list.member,您要呼叫的成员。至于真假,你会的 还需要定义这些名称的谓词。(默认情况下, 它们只作为目标存在。)