Использовать мета-предикат texclude/3
в сочетании с предикатом равенства термина reified (=)/3
!
Сначала мы попробуем использовать (=)/3
напрямую ...
?- texclude(=((1,V)), [(1,1),(1,2),(3,2)], KVs).
KVs = [ (1,2),(3,2)], V=1 ;
KVs = [(1,1), (3,2)], V=2 ;
KVs = [(1,1),(1,2),(3,2)], dif(V,1), dif(V,2).
Не совсем! Для наших следующих попыток мы будем использовать лямбда-выражения .
:- use_module(library(lambda)).
Давайте запросить --- один раз с texclude/3
, один раз с tinclude/3
и один раз с tpartition/4
:
?- texclude( \ (K,_)^(K=1), [(1,1),(1,2),(3,2)], Fs).
Fs = [(3,2)]. % succeeds deterministically
?- tinclude( \ (K,_)^(K=1), [(1,1),(1,2),(3,2)], Ts).
Ts = [(1,1),(1,2)]. % succeeds deterministically
?- tpartition(\ (K,_)^(K=1), [(1,1),(1,2),(3,2)], Ts,Fs).
Ts = [(1,1),(1,2)], Fs = [(3,2)]. % succeeds deterministically
Хорошо! Получим ли мы те же решения, если элементы списка связаны после texclude/3
вызова?
?- texclude(\ (K,_)^(K=1), [A,B,C], Fs), A = (1,1), B = (1,2), C = (3,2).
A = (1,1), B = (1,2), C = (3,2), Fs = [(3,2)] ; % succeeds with choice point
false.
Да! Наконец, рассмотрим следующий довольно общий запрос:
?- texclude(\ (K,_)^(K=1), [A,B], Fs).
Fs = [ ], A = ( 1,_A1), B = ( 1,_B1) ;
Fs = [ B], A = ( 1,_A1), B = (_B0,_B1), dif(_B0,1) ;
Fs = [A ], A = (_A0,_A1), B = ( 1,_B1), dif(_A0,1) ;
Fs = [A,B], A = (_A0,_A1), B = (_B0,_B1), dif(_A0,1), dif(_B0,1).
Обратите внимание, что вышеуказанные цели ограничивают все элементов списка, чтобы иметь форму(_,_)
.Таким образом, следующий запрос не выполняется:
?- texclude(\ (K,_)^(K=1), [x,_], _).
<b>false</b>.