Простой Пролог удалить из списка - PullRequest
5 голосов
/ 22 июня 2011

(Это не вопрос курсовой работы. Просто мое личное обучение.)

Я пытаюсь выполнить упражнение в Прологе, чтобы удалить элементы из списка. Вот мой код:

deleteall([],X,[]).
deleteall([H|T],X,Result) :- 
    H==X,
    deleteall(T,X,Result).
deleteall([H|T],X,[H|Result]) :- deleteall(T,X,Result).

Когда я проверяю его, я сначала получаю хороший ответ (т. Е. Со всеми удаленными X). Но затем при возврате мне предлагаются все другие варианты списка с некоторыми или ни с одним удаленным экземпляром X.

Почему это должно быть? Почему случаются случаи, когда H == X доходит до последнего предложения?

Ответы [ 2 ]

6 голосов
/ 22 июня 2011

Когда вы используете (==)/2 для сравнения, вам понадобится противоположность в третьем правиле, то есть (\==)/2.С другой стороны, такое определение уже не является чистым отношением.Чтобы увидеть это, рассмотрим deleteall([X],Y,Zs), X = Y.

. Для чистого отношения нам понадобятся (=)/2 и dif/2.Многие прологи, такие как SWI, YAP, B, SICStus, предлагают dif/2.

deleteall([],X,[]).
deleteall([H|T],X,Result) :- 
    H=X,
    deleteall(T,X,Result).
deleteall([H|T],X,[H|Result]) :-
    dif(H,X),
    deleteall(T,X,Result).

Посмотрите ответы на deleteall([X,Y],Z,Xs)!

Правка (через четыре года):

Более эффективно, но в том же духе, это можно записать с помощью if_/3 и (=)/3:

deleteall([], _X, []).
deleteall([E|Es], X, Ys0) :-
   if_( E = X, Ys0 = Ys, Ys0 = [E|Ys] ),
   deleteall(Es, X, Ys).
2 голосов
/ 22 июня 2011

В последнем предложении говорится, что при удалении X из списка элемент head может остаться (независимо от его значения).Prolog может использовать это предложение в любое время, когда сочтет нужным, независимо от того, является ли условие в предыдущем предложении истинным или нет вернуться в это предложение, если другое предложение не выполнено, или если вы поручили это сделать (например,введя ; на верхнем уровне, чтобы получить следующее решение).Если вы добавите условие, что элемент head может не равняться X, он должен работать.

Редактировать: Удалено неверное утверждение, которое я первоначально открыл.

...