使用SWI-Prolog的列表谓词(或列表库中的SICStus'谓词),我们有:
lists:subtract([], _, []) :- !.
lists:subtract([A|C], B, D) :-
memberchk(A, B), !,
subtract(C, B, D).
lists:subtract([A|B], C, [A|D]) :-
subtract(B, C, D).
成功地做到了这一点:
?- subtract([2,3,4,5],[3,4],X).
X = [2, 5].
但是,如果我想这样做:
?- new_subtract([2,3,4,5],[3,X],Y).
X = [3, 2],
X = [3, 4],
X = [3, 5],
Y然后通过[2,3,4,5]中的三个X解决方案得到三个解决方案。
但是,减去/ 2不允许这样做。
我一直试图通过从内置谓词的主体中删除(!)来尝试解决这个问题,并试图让它回溯并找到所有解决方案。
答案 0 :(得分:4)
我认为你的意思是
?- new_subtract([2,3,4,5],[3,X],Y).
Y = [3, 2] ;
Y = [3, 4] ;
Y = [3, 5]
以下定义可以做到这一点,但不会保留subtract/3
的所有行为:
sub(List,[],List).
sub(List,[X|Sub],Rem) :- select(X,List,Rem0), sub(Rem0,Sub,Rem).
用法:
?- sub([2,3,4,5],[3,X],Y).
X = 2,
Y = [4, 5] ;
X = 4,
Y = [2, 5] ;
X = 5,
Y = [2, 4] ;
false.