Листинг6.1.1. Поиск нужного элемента(принадлежность списку)

domains

list=integer*

predicates

member(integer,list)

clauses

(1) member(Head,[Head|_]).

(2)member(Head,[_|Tail]):-

member(Head,Tail).

 

Алгоритм: (декларативная точка зрения)

Элемент принадлежит списку, если

(1) первый элемент списка и есть искомый элемент

(2) искомый элемент входит в состав хвоста списка

С процедурной точки зрения предложения программы 1 и 2 можно трактовать так: чтобы найти принадлежность элемента списку, надо проверить, не совпадает ли элемент с головой списка и если нет, то попытаться найти этот элемент в хвосте списка.

Цели

? member(3,[5,6,3,8,9]) –просим Пролог выяснить верно ли это утверждение.

(ответ: Yes или No в зависимости от того, входит или нет элемент с состав списка)

? member(X,[6,8,9])- вывод всего списка

И процедурная и декларативная точки зрения соотносятся с целями 1 и 2.

(ответ:

X=6

X=8

X=9

)

Модифицируем первое предложение member(Head,[Head|__]):-!.

Как изменится ответ, если поставим цель ?member(X,[6,8,9])

(ответ: X=6- только одно решение) Отсечение не позволит нам получить оставшиеся элементы списка, следовательно, это можно использовать только для получения одного конкретного значения –первого элемента списка.

Проверим, имеет ли значение порядок написания двух предложений для предиката member()? Поменяем местами эти предложения. Поставим цель member(X,[6,8,9]).Ответ будет напечатан в обратном порядке:

(ответ:

X=9

X=8

X=6

)

Убедились, что с процедурной точки зрения порядок предложений в программе важен. Изменение порядка правил в процедуре приведет к перестановке ветвей в дереве поиска цели, использующей данную процедуру. Само дерево поиска не изменится, но обход деревабудет производиться в ином порядке, а значит и процесс унификации пойдет иначе.

Замечание: Порядок целей более существенен, чем порядок предложений. Порядок целей имеет решающее значение при определении последовательности действий в программе. Изменение порядка целей приведет к изменению дерева поиска.