Больше детерминизма для `memberd / 2`?
Многие системы обеспечивают чистую и эффективную реализациюmember/2
, В частности, точка выбора не остается открытой для:
?- member(b,[a,b]).
true.
в то время как наивная реализацияmember/2
производит скорее:
?- member(b,[a,b]).
true ;
false.
что, безусловно, правильно с декларативной точки зрения, но менее эффективно.
С другой стороны, есть некоторые технические проблемы сmember/2
, Это позволяет избыточные решения, как в:
?- member(a,[a,a]).
true ;
true.
memberd/2
решает эту проблему с помощьюif_/3
а также(=)/3
.
memberd(E, [X|Xs]) :-
if_(E = X, true, memberd(E, Xs)).
?- memberd(a,[a,a]).
true.
К сожалению, это определение оставляет точки выбора снова открытыми - производя; false
(«оставшиеся точки выбора») в ситуациях, когда член не делает:
?- memberd(X,[a,b]).
X = a ;
X = b ;
false. % BAD - to be avoided!
?- member(X,[a,b]).
X = a ;
X = b.
Итак, мой вопрос: есть ли определениеmemberd/2
что позволяет избежать выбора пункта, как этот выше?