У.Клоксин, К.Меллиш ПРОГРАММИРОВАНИЕ НА ЯЗЫКЕ ПРОЛОГ Для программистов и пользователей ЭВМ.

ПРЕДИСЛОВИЕ РЕДАКТОРОВ ПЕРЕВОДА

Язык программирования Пролог появился в 1970 г. одновременно с такими сейчас широко распространенными языками, как Паскаль и Си. Его ориентация – «нетрадиционные» применения вычислительной техники: понимание естественного языка, базы знаний, экспертные системы и другие задачи, которые принято относить к проблематике искусственного интеллекта. Сила этого языка – в принципиально отличном от традиционных языков программирования подходе к описанию способа решения задачи: программа на Прологе описывает не процедуру решения задачи, а логическую модель предметной области – некоторые факты относительно свойств предметной области и отношений между этими свойствами, а также правила вывода новых свойств и отношений из уже заданных. Таким образом, Пролог – описательный язык. Как отмечено в авторском предисловии, такой логический подход к программированию создает и некоторые проблемы в распространении языка: основные понятия языка опытными программистами понимаются без труда, однако практическое претворение этого понимания в полезные программы вызывает затруднения.

Несмотря на очевидные и яркие достоинства, Пролог, в отличие от своих «сверстников» (Паскаля и Си), продолжительное время развивался, применялся и обсуждался в сравнительно узком кругу исследователей, работающих в области искусственного интеллекта. И лишь в последние годы Пролог попал в поле зрения широких кругов специалистов по информатике. Резкий рост его популярности объясняется, по-видимому, выходом теории искусственного интеллекта в область практического, «коммерческого» программирования.

В настоящее время растет круг практических систем, использующих достижения искусственного интеллекта на современных ЭВМ, появились престижные национальные проекты создания ЭВМ новых поколений, в которых интеллектуальный интерфейс с конечным пользователем (непрофессионалом в информатике) является центральным элементом. В японском проекте создания ЭВМ пятого поколения Пролог прямо называется базовым языком программирования. По-видимому, Пролог реально претендует на роль одного из основных инструментальных языков для «нетрадиционных» применений вычислительной техники, поэтому своевременное знакомство с ним отечественных специалистов, работающих в данной области, будет несомненно полезным.

В социалистических странах активное участие в разработках, связанных с Прологом, принимают ученые ВНР. В Институте по координации вычислительной техники (г. Будапешт) создана версия Пролога – МПролог, получившая международное признание. Не исключено, что МПролог будет широко доступен и пользователям нашей страны. Этим объясняется включение в русское издание специального приложения (F) посвященного МПрологу.

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

Предисловие, главы 1,3-6, 9, 10 и Приложение В перевел М. М. Комаров, главы 7, 8, 11, Приложения А,С, D, E, F- А. В. Горбунов, главу 2 – Ю. М. Лазутин.

ПРЕДИСЛОВИЕ КО ВТОРОМУ ИЗДАНИЮ

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

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

У. Клоксин К. Меллиш

Кембридж, Англия, август 1984

ПРЕДИСЛОВИЕ К ПЕРВОМУ ИЗДАНИЮ

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

• реляционные базы данных,

• математическую логику,

• решение абстрактных задач,

• понимание естественного языка,

• автоматизацию проектирования,

• символьное решение уравнений,

• анализ биохимических структур,

• различные области искусственного интеллекта.

До настоящего времени не было книг, ставивших своей целью обучить Прологу как языку практического программирования. Видимо, Пролог оказался настолько привлекательным для многих людей, что они стали его изучать, используя неизбежно краткие справочные руководства, небольшое число опубликованных статей и передаваемый устно среди пользователей языка «фольклор». Однако с внедрением Пролога в учебные программы для студентов и аспирантов многим из наших коллег понадобилось учебное руководство по Прологу. Мы надеемся, что наша небольшая книга до некоторой степени удовлетворит эту потребность.

Многие новички обнаруживали, что задача написания программы на Прологе не похожа на спецификацию алгоритма при программировании на традиционном языке программирования. Программист, использующий Пролог, больше интересуется тем, какие формальные отношения и объекты имеют место в решаемой задаче и какие отношения справедливы для разыскиваемого решения. Таким образом, Пролог можно рассматривать как язык описаний, а не как языкпредписаний. Используемый в Прологе подход состоит главным образом в описании известных фактов и отношений, касающихся решаемой задачи, а не в предписании последовательности шагов, выполняя которые ЭВМ решит задачу. При реализации программы на Прологе фактическая последовательность вычислений, выполняемая ЭВМ, определяется частично логической декларативной семантикой Пролога, частично новыми фактами, которые Пролог может «вывести» из заданных ему фактов, и лишь отчасти управляющей информацией, явно заданной программистом.

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

Эта книга может служить нескольким целям. Мы не собираемся учить искусству программирования как таковому. Нам кажется, что нельзя научиться программированию, просто читая книги или слушая лекции. Вы должны программировать,чтобы научиться делать это. Мы надеемся, что начинающие программисты, не имеющие математической подготовки, смогут освоить Пролог по этой книге, хотя в этом случае мы советовали бы, чтобы начинающий программист осваивал язык под руководством программиста, знающего Пролог, в рамках вводного курса по программированию как таковому. Предполагается, что начинающий программист может получить доступ к ЭВМ, на которой имеется Пролог-система, и что он прошел необходимый инструктаж по работе с терминалом. Опытному программисту не потребуется дополнительная помощь, но он также не должен впадать в уныние от наших усилий ограничить математические излишества. Мы использовали предварительный вариант этой книги при обучении выпускников университета, имевших математическую подготовку на уровне школьной программы и специализировавшихся в университете по философии и психологии.

Наш опыт показывает, что начинающим программы на Прологе представляются более понятными, чем соответствующие программы на традиционных языках программирования. Однако те же самые люди не склонны ценить те ограничения, которые накладывают традиционные языки на использование вычислительных ресурсов. С другой стороны, программист, имеющий опыт работы на традиционных языках программирования, лучше подготовлен к восприятию таких абстрактных понятий, как переменные и управление последовательностью действий. Но, несмотря на прежний опыт, приспособление к стилю программирования на Прологе может вызвать у него затруднения, и может потребоваться много убедительных примеров, прежде чем он начнет относиться к Прологу как к полезному средству программирования. Конечно, мы знаем много высококвалифицированных программистов, воспринявших Пролог с большим энтузиазмом. Тем не менее, цель этой книги не в том, чтобы «обратить в иную веру», а в том, чтобы научить программировать на Прологе.

Как и большинство других языков программирования, Пролог существует в множестве различных реализаций, каждая со своими семантическими и синтаксическими особенностями. Для описания в этой книге выбран «базовый» Пролог и все приводимые примеры написаны для стандартной версии, которая соответствует реализациям, разработанным главным образом в Эдинбурге для нескольких различных вычислительных систем: DEC-10 с операционной системой TOPS-10, DEC VAX и PDP-11 с операционной системой Unix, DEC LSI-11 с операционной системой RT-11 и ICL2980 с операционной системой ЕМА. Реализации для ЭВМ фирмы DEC являются, вероятно, наиболее распространенными. Все примеры, приведенные в этой книге, подходят для всех указанных реализаций. В приложениях приведены описания некоторых из существующих реализаций Пролога с указанием их отличий от стандарта. Читатель сможет убедиться, что большинство отличий имеет чисто «косметическую» природу.

Книга построена таким образом, что читать ее надо последовательно. Тем не менее, будет полезно прочитать гл. 8 в тот момент, когда читатель начнет писать программы на Прологе, состоящие более чем из десяти утверждений. Кроме того, разумно прочитать соответствующее приложение, содержащее описание используемой реализации Пролога. В приложениях говорится, как вводить утверждения, какие средства отладки имеются в системе, и рассматриваются другие практические вопросы. Не будет особого вреда, если вы лишь просмотрите книгу, но старайтесь при этом не пропускать главы.

Каждая глава книги делится на несколько разделов, и мы советуем читателю выполнять упражнения, приводимые в конце многих разделов. Решения к некоторым из этих упражнений даны в конце книги. Глава 1 представляет собой введение, цель которого – дать читателю почувствовать характер программирования на Прологе. Здесь вводятся основные идеи языка Пролог и читателю рекомендуется тщательно изучить их. В гл. 2 содержится более полное обсуждение идей и понятий, введенных в гл. 1. В гл. 3 рассматриваются структуры данных и приводятся в качестве примеров несколько небольших программ. В гл. 4 более подробно обсуждается механизм возврата, вводится символ «отсечения», используемый для управления механизмом возврата. В гл. 5 вводятся имеющиеся в языке средства ввода-вывода. В гл. 6 описывается каждый встроенный предикат базовой версии языка Пролог. Глава 7 представляет собой «попурри» из примеров программ, взятых из многих источников и снабженных комментариями, поясняющими их работу. В гл. 8 даются некоторые советы по отладке программ на Прологе. В гл. 9 вводится синтаксис грамматических правил и изучаются предположения, лежащие в основе программ для анализа естественного языка с использованием грамматических правил. В гл. 10 описывается связь Пролога с идеями математического доказательства теорем и логического программирования, лежащими в основе языка. В гл. 11 представлен ряд проектов, на которых заинтересованные читатели могут поупражняться в развитии навыков программирования на Прологе.

Мы выражаем благодарность нашим учителям, сформировавшим наши взгляды на программирование: Роду Борстоллу, Питеру Скотту Лэнгстону и Робину Попплстоуну. Мы благодарны друзьям, участвовавшим вместе с нами в совершенствовании Пролога как практического и полезного средства программирования и поддерживавших нас в процессе подготовки этой книги: Алану Банди, Лоренсу Байрду, Роберту Ковальски, Фернандо Перейра и Дейвиду Уоррену. В частности, Лоуренс Байрд поддерживал работу по созданию книги с самого ее начала, предлагая программы, упражнения, некоторые проекты, приведенные в гл. 11, и много идей по организации книги. Мы также благодарны нашим друзьям, внесшим свой вклад в создание книги полезными замечаниями и советами по улучшению предварительного ее варианта: Джону Каннингаму, Ричарду О'Кифу, Элен Пейн, Фернандо Перейра, Гордону Плоткину, Роберту Реи, Питеру Россу, Максвеллу Шортеру, Арону Сломену и Дейвиду Уоррену. В этом отношении У. Клоксин особенно благодарен своим аспирантам из School of Epistemics и Department of Artificial Intelligence, которые помимо их воли стали объектом многочисленных экспериментов в области обучения программированию. При выборе примеров мы свободно пользовались распространенным программистским фольклором и в связи с этим приносим наши извинения всем, кто чувствует себя обойденным вниманием.

Эта книга была подготовлена в период работы авторов на факультете искусственного интеллекта Эдинбургского университета. Мы благодарны Джиму Хоу, возглавлявшему факультет, за создание благоприятных условий при работе над книгой.

У. Клоксин К. Меллиш

Эдинбург, Шотландия, июнь 1981

ГЛАВА 1 ВВЕДЕНИЕ

Пролог – язык программирования, используемый для решения задач, сводимых к объектам и отношениям между объектами. В этой главе мы продемонстрируем основные элементы языка на примерах реальных программ, не вдаваясь особенно в детали, формальные правила и исключения. Исходя из этого, мы не старались, чтобы изложение было полным или достаточно точным. Мы хотим как можно быстрее подвести вас к тому моменту, когда вы сможете самостоятельно писать полезные программы, и чтобы добиться этого, мы должны сконцентрировать внимание на основных понятиях: фактах, запросах, переменных, конъюнкциях и правилах. Другие особенности языка Пролог, такие как списки и рекурсия, будут рассмотрены в последующих главах.

Пролог применяется в тех случаях, когда необходимо использовать ЭВМ для решения задачи, которая может быть выражена в терминах объектов и отношений между ними. Например, когда мы говорим: «Джон имеет книгу», мы объявляем, что между одним объектом «Джон» и другим объектом «книга» имеет место отношение обладания. Более того, это отношение имеет определенный порядок: Джон имеет книгу, но книга не имеет Джона! Когда мы задаем вопрос: «Имеет ли Джон книгу?», то нас интересует правильность именно отношения.

При констатации некоторых отношений не всегда упоминаются все объекты, включаемые в них. Например, когда мы говорим: «Драгоценные камни являются ценными», мы имеем в виду, что существует отношение, называемое «являться ценным», которое включает драгоценные камни. Для нас не имеет значения, кто считает, что драгоценные камни являются ценными, и почему он так считает. Это все зависит от того, что вы хотите сказать. При использовании Пролога, когда программируются отношения, подобные приведенным, уровень требуемой детализации также зависит от того, что вы хотите заставить делать ЭВМ.

Существует еще один вопрос идейного плана, который следует упомянуть,прежде чем приступать к программированию. Мы все знакомы с использованием правил для описания отношений между объектами. Например, правило «Два человека являются сестрами, если они оба женского пола и имеют одних и тех же родителей» объясняет нам, что значит быть сестрами. Оно также указывает, как определить, являются ли два человека сестрами: необходимо просто проверить, относятся ли они оба к женскому полу и имеют ли одних и тех же родителей. Важно отметить, что хотя правила обычно бывают упрощенными, тем не менее они приемлемы в качестве определений. В конце концов, не следует ожидать, что определение говорит нам все об определяемом объекте. Например, большинство людей согласится с тем, что в реальной жизни «быть сестрами» значит больше, чем это следует из приведенного правила. Однако, решая конкретную задачу, необходимо сосредоточить внимание именно на таких правилах, которые помогут ее решить. Таким образом, следует обратиться к схематичному и упрощенному определению, если его достаточно для достижения поставленной цели.

Программирование на языке Пролог состоит из следующих этапов:

• объявления некоторых фактов об объектах и отношениях между ними,

• определения некоторых правил об объектах и отношениях между ними и

• формулировки вопросов об объектах и отношениях между ними.

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

Пролог является диалоговым языком. Это следует понимать так, что пользователь и ЭВМ осуществляют некоторое подобие диалога. Предположим, что вам предложили поработать за терминалом ЭВМ и воспользоваться Прологом. Ваш терминал состоит из клавиатуры и дисплея. Вы используете клавиатуру для ввода информации в ЭВМ, а ЭВМ использует дисплей (может быть, экран либо бумажную ленту) для вывода полученных результатов. Пролог будет ждать, пока вы введете факты и правила, относящиеся к задаче, которую вы хотите решить. Затем, если вы сможете задать вопросы и если вы делаете это правильно, Пролог будет искать соответствующие ответы и выводить их на дисплей.

Теперь мы последовательно введем каждое из основных понятий языка Пролог. Не беспокойтесь о том, что вы не получите сразу полного представления о всех особенностях языка Пролог. В последующих главах будет дано их исчерпывающее описание и будет приведено и разобрано много примеров решения задач на языке Пролог.