Добавил:
Upload Опубликованный материал нарушает ваши авторские права? Сообщите нам.
Вуз: Предмет: Файл:
Учебное пособие Функциональное и логическое программирование.docx
Скачиваний:
4
Добавлен:
01.07.2025
Размер:
309.57 Кб
Скачать

Простейшая программа на Прологе

Программа состоит из множества фраз (прдложений). Каждая фраза - это факт, правило или вопрос.

Факт - это утверждение о том, что соблюдается некоторое конкретное отношение между объектами. Факт - это фраза без условий, т.е. это утверждение, которое всегда истинно. Факт состоит из имени предиката и списка аргументов(термов), заключенного в скобки.

Предикат - это абстрактный смысл существующего отношения между некоторым количеством аргументов. Предикат отражает множество объектов на множество {истина, ложь}. Обычно выбирается такое имя предиката, чтобы оно отражало вид взаимосвязи между аргументами. Предикат может обладать произвольным количеством аргументов. Одноместный предикат просто указывает свойство объекта.

Вопрос – цель выполнения программы: ?- Факт с переменными.

Простейшая Пролог-программа - это множество фактов, которое неформально называют базой данных. Пример базы данных, состоящей из фактов «знает»:

знает(маша, паша).

знает(коля, оля).

знает(паша, оля).

Совокупность этих фактов определяет двуместный (бинарный) предикат «знает».

Правило - это факт (заголовок правила), истинность которого зависит от истинности условий, указанных в его условной части (тело правила). Заголовок правила имеет такую же форму, как и факт, затем стоит обозначение ":-" (если), за которым располагается тело правила. Каждое условие, входящее в правило, называется подцелью. Условия разделяются знаком « , », означающим логическое И. Для того чтобы заголовок правила был истинным, необходимо, чтобы каждое условие, входящее в тело правила (каждая подцель), была истинной. Правило, в которое входят переменные, можно рассматривать как неявное определение множества фактов. Предположим, создана база данных «проживает»:

проживает ( петров, кирова, 41, 5).

проживает ( сидоров, ленина, 15, 18).

проживает ( иванов, мира, 21, 6).

проживает ( федоров, мира, 21, 8).

Следующее правило позволяет установить, что два человека знают друг друга, если они живут в одном доме:

знает(X, Y):-

проживает(X, Z1, Z2, _ ),

проживает(Y, Z1, Z2, _ ).

Рассмотрим отношение «родитель». Введем отношения «мужчина» и «женщина». Запишем факты этих отношений. Теперь введем новые правила в программу:

отпрыск (А, В):-

родитель(В, А).

мать (А, В):-

родитель(А, В),

женщина(А).

дедушка (А, В):-

родитель(А, С),

родитель(С, В),

мужчина(А).

сестра (А, В):-

родитель(С, А),

родитель(С, В),

женщина(А),

различны(А, В).

родитель_родителя(А, В):-

родитель(А, С),

родитель(С, В).

Теперь системе можно задавать вопросы, называемые запросами. Простой запрос состоит из имени предиката, за которым располагается список аргументов. Запрос - это всегда последовательность одной или нескольких целей. Чтобы выполнить запрос, система пытается достичь всех целей. Достичь цели - значит показать, что утверждения, содержащиеся в запросе, истинны в предположении, что все отношения программы истинны, т.е. целевое утверждение логически следует из фактов и правил программы.

Система рассматривает множество фактов и правил программы как аксиомы, а запрос как теорему, и пытается доказать теорему, т.е. показать, что ее можно логически вывести из аксиом.

Если в запрос не входят переменные, то система ответит «да» или «нет». Ответ «да» говорит о том, что интерпретатор смог доказать истинность запроса в соответствии с множеством фраз программы - цель достижима. «Нет» означает, что интерпретатор не смог доказать истинность запроса - цель недостижима.

Если в запрос входят переменные, то система должна найти конкретные объекты, которые, будучи подставлены на место переменных, позволяют достичь цели. Если такие конкретные объекты найдены, то говорят, что переменные конкретизируются, а их конкретные значения сообщаются пользователю. Переменные запроса существуют столько же, сколько и сам запрос. Системе можно задавать составные запросы:

?- родитель(миша, А), родитель(маша, А ). есть ли общий ребенок ?

?- родитель(А, коля), родитель(А, петя). есть ли общий родитель ?

?- родитель(А, _ ). выдает все значения первого аргумента вне зависимости от того, какие значения будет принимать второй аргумент.

Пример. Структура "клиент" и структура "дата" являются аргументами факта "сделка":

сделка ( клиент ( смит, 29 , 4 ), дата ( 86 , 4 , 22 ) ).

Факт «сделка» связывает информацию о сделке с клиентом и дату, когда эта сделка была заключена.

Составим правило, в котором аргументом служит структура "клиент". В результате обработки правила подсчитывается общая сумма, которую должен заплатить клиент (т.е. суточный тариф, умноженный на количество дней):

итого (клиент(_, Тариф,Дни), Сумма):-

Сумма is Тариф * Дни.

Фамилия не требуется для вычисления суммы оплаты, поэтому первый аргумент структуры «клиент» обозначен символом "_". Запрос к правилу может быть таким:

?- итого ( клиент ( смит , 29 , 4) , С).

Ответ: С=116