Описанные выше возможности языка Пролог для работы с базой фактов во многом совпадают с возможностями, предоставляемыми системами управления реляционными базами данных. Языком представления знаний Пролог делают имеющиеся в нем средства для описания базы правил. Правило представляет собой дизъюнкт Хорна, содержащий один положительный литерал и несколько отрицательных, и записывается следующим образом:
<структура-0> :- <структура-1>, ..., <структура-N>.
Здесь каждая структура представляет собой предикат, областью действия переменных является все правило. Предикат, стоящий слева от атома ":-" , называется заголовком правила, все остальные предикаты образуют его тело. Правило может трактоваться следующим образом: предикат, являющийся заголовком правила, истинен (удовлетворен) тогда, когда истинен каждый из предикатов тела правила.
Пример 1
Правила, задающие различные допустимые конструкции башен в рассматриваемой нами предметной области, записываются на языке Пролог так, как это показано ниже.
tower(Fr, Fc, Nbl, H) :- roof(Fr, Hr), col(Fc, Nbl, Hc), H is Hr + Hc.   /* 7 */
col(F, 1, H) :- block(F, H).                                             /* 8 */
col(F, 2, H) :- block(F, H1), block(F, H2), H is H1+H2.                  /* 9 */
col(F, 3, H) :- block(F, H1), block(F, H2), block(F, H3), H is H1+H2+H3. /* 10 */
Здесь переменные в утверждении 7 имеют такой смысл: Fr -форма крыши башни, Fc - форма блоков ствола башни, Nbl - количество блоков в башне, H - высота башни, Hr - высота крыши, Hc - высота ствола. В утверждениях 8 ... 10 переменная F означает форму блоков ствола, H - высоту ствола, H1, H2, H3 - высоту блоков. Напомним, что область действия переменной ограничена только одним утверждением, поэтому, например, переменная H в правилах 7 и 8 означают разные объекты.
Часто при интерпретации правил атом ":-" удобно читать как "это есть". Тогда правило 7 может быть прочитано следующим образом: башня высотой Н , состоящая из Nbl блоков формы Fc и имеющая крышу формой Fr - это есть крыша формой Fr и высотой Hr, ствол высотой Hc, состоящий из Nbl блоков формы Fc, и высота башни H равна сумме высот крыши Hr и ствола Hc.
Наличие правил в программах на языке Пролог позволяет интерпретатору находить ответ на запросы, не касающиеся непосредственно содержимого базы фактов. В вашей предметной области таким запросом может быть, например, запрос на конструирование башни высотой 11 из блоков цилиндрической формы:
?-tower(F_roof, cyl, N_blocks, 11).
Первым ответом будет F_roof = plane, N_blocks = 2. Рассмотрим процесс получения ответа. Интерпретатор, получив запрос, осуществляет поиск предиката tower среди фактов и заголовков правил. В нашем случае будет найдено правило (утверждение 7), в результате сопоставления заголовка правила и запроса будут конкретизированы переменные правила Fc и H (значениями cyl и 11, соответственно) и связаны переменные F_roof и Fr, а также N_blocks и Nbl.
В результате возникают 3 новые подцели, которые необходимо удовлетворить. Интерпретатор начинает с крайней левой - roof(Fr, Hr). Эта подцель согласуется с первым утверждением базы, переменные Fr и связанная с ней F_roof конкретизируются значением prizm, а переменная Hr - значением 4.
Далее интерпретатор возвращается к предикату col(cyl, Nbl, Hc) правила 7 и, рассматривая его как подцель, пробует согласовать с базой правил и фактов. Первым подходящим для согласования утверждением является восьмое - правило, описывающее стволы из одного блока. Этим блоком является цилиндр высотой 5 (утверждение 3). В результате конкретизации переменная Nbl принимает значение 1, а переменная Hc - 5.
Предикат проверки равенства (третья подцель в правиле 7) является встроенным, его истинность интерпретатор проверяет, не обращаясь к базе утверждений. Поскольку H имеет значение 11, Hr - 4, а Hc - 5, то эта подцель неудовлетворена и происходит возврат к соседней слева подцели (col) с тем, чтобы попытаться согласовать ее заново. Эта попытка приводит к тому, что в качестве ствола выбирается ствол, состоящий из одного блока цилиндрической формы, но высотой 3 (а не 5, как ранее). Ясно, что значением предиката равенства по-прежнему будет ложь и вновь потребуется пересогласование подцелей.
Таким образом, интерпретатор осуществит полный перебор вариантов построения башни с призматической крышей и вынужден будет использовать в конструкции башни плоскую крышу. Этот выбор в конечном итоге и обеспечит получение ответа на запрос.
Рассмотренные примеры позволяют сделать ряд важных заключений, касающихся языка Пролог. Во-первых, язык Пролог позволяет создавать программы, обладающие свойством недетерминизма, т.е. программы, способные давать ответы на запросы, в которых априорно не фиксируются объекты, являющиеся исходными и результирующими. Так, для нашей программы с башнями вполне корректен будет запрос на проектирование башни с призматической крышей из трех блоков:
?-tower(prizm, F, 3 ,H).
Во-вторых, утверждения программ на языке Пролог в значительной степени независимы друг от друга, что позволяет легко модифицировать программы, пополняя и изменяя факты и правила.
В-третьих, интерпретатор системы программирования Пролог, реализуя линейную по входу версию метода резолюции, осуществляет поиск ответа на запрос полным перебором, используя стратегию поиска в глубину. Для реализации режима с возвращением применяется механизм бэктрекинга. С целью сокращения количества вариантов перебора в больших программах на языке Пролог целесообразно включать в правила условия эвристического характера.
Пример 2
Эффективность исполнения нашей программы при выполнении запросов, связанных с конструированием башни требуемой высоты, значительно повысится, если правила будут переписаны следующим образом.
tower(Fr,Fc,Nbl,H):-roof(Fr,Hr),Hc is H-Hr,col(Fc,Nbl,Hc).
col(F,1,H):-H>1,H<6,block(F,H).
col(F,2,H):-H>3,H<11,block(F,H1),H2 is H-H1,block(F,H2).
col(F,3,H):-H>5,H<16,block(F,H1),block(F,H2),H3 is H-H1-H2,block(F,H3).
Введение в правила 7 ... 10 предикатов меньше и больше сузило их "область применения" и тем самым уменьшило количество вариантов перебора при поиске ответа, но лишило программу двух важных свойств - недетерменизма и независимости утверждений в базах. Так, теперь стали невыполнимы запросы на проектирование башен произвольной высоты.
Рассмотренная предметная область является конечной, поскольку количество вариантов конструкций башен в ней ограничено. Но предположим, что в ней допустимы башни, стволы которых могут состоять из неограниченного количества блоков. Понятно, что это обстоятельство невозможно отразить правилами, подобными правилам 8 ... 10. Возникает необходимость в рекурсивном определении правил для ствола.
col(F, 1, H) :- block(F, H).
col(F, Nbl, H) :- block(F, Hbl), col(F, N, Hc), H is Hbl+Hc, Nbl is N+1.
Это определение интерпретируется следующим образом: 1) ствол - это есть один блок, при этом форма и высота ствола совпадают с формой и высотой блока, или 2) ствол - это есть блок и "подствод", при этом высота ствола равна сумме высот блока и "подствола", а количество блоков в стволе на единицу больше, чем в "подстволе". Пара этих утверждений способна породить ствол из любого количества блоков.
Необходимо отметать, что использование рекурсивных определений такого типа в программах на языке Пролог связано с опасностью бесконечного "зацикливания" в рекурсиях. Такой, например, будет ситуация в нашем примере при запросе на конструирование башни высотой 11, когда интерпретатор будет исследовать бесконечное число проектов башен с призматической крышей и цилиндрическим стволом высотой кратной пяти. В этом проявляется упомянутое ранее свойство полуразрешимости ИППП, лежащего в основе языка Пролог.
Отмеченные достоинства языка Пролог - декларативная форма представления знаний о предметной области, недетерминизм, легкая модифицируемость программ - обусловили его широкое применение в различных проектах ИИ. Системы программирования Пролог имеются для всех универсальных ЭВМ.