суббота, 24 ноября 2012 г.

Prolog #2.2

Погружение в Prolog

2.2 Среда SWI-Prolog 

    Версия Prolog, которую мы будем использовать называется SWI-Prolog. Она разработана в Шведском Институте Компьютерных Наук(Computer Science). Данная среда является интерактивной системой, по типу Hugs, среды для языка функционального программирования, Haskell. SWI-Prolog можно запускать в двух разных режимах: из командной строки, или через интерфейс, основанный на Emacs. В обоих случаях, перед тем как двигаться дальше, вам следует добавить следующую строку в секцию синонимов(alias) вашего .cshrc файла(файла, который запускается тогда, когда ваша рабочая оболочка запускается)(актуально для *nix систем):

        alias prolog '/usr/local/bin/prolog -f none'

    Не забудьте активировать данный синоним(alias), введя команду оболочки:

        source `/.cshrc

Emacs - пропустите, если не используете Emacs.

    Существует режим GNU Emacs для SWI-Prolog. Если вы не будете использовать Prolog в Emacs редакторе, то можете пропустить данный раздел. 
    Для начала вы должны добавить следующие строки(в приведенном виде) в ваш .emacs файл в домашней директории. Введите эти строки в секции, помеченной "Hooks".

        (setq auto-mode-alist (append
                                          (list
                                           (cons "\\.pl$" ’prolog-mode))
                                          auto-mode-alist))
        (autoload ’prolog-mode "~/emacs/prolog.el" "" t)

    Если вы добавили эти строки и загружаете файл, чье имя заканчивается на '.pl', Emacs автоматически войдет в режим редактирования программ Prolog.
    Для того, чтобы использовать этот режим, вы создаете свою программу, дав файлу с исходным кодом расширение .pl. Как только вы создали программу, вы можете вызвать интерпретатор с помощью команды:

        Control-c Shift-c

    Это активирует Prolog, и в то же время, загрузит ваш файл в интерпретатор  Когда загрузка закончится, вы можете начать задавать вопросы системе Prolog. Помните, что каждое правило в Prolog, так же как и запрос, оканчивается точкой.
    Режим Prolog в Emacs предоставляет следующие команды:

        M-x run-prolog        Запускает внутренний процесс Prolog,
                                        ввод и вывод через буфер *prolog*.
        C-c K                      prolog-compile-buffer
        C-c k                       prolog-compile-region
        C-c C-k                   prolog-compile-predicate
        C-c C                      prolog-consult-buffer
        C-c c                       prolog-consult-region
        C-c C-c                   prolog-consult-predicate

Использование интерпретатора


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

        |  ?-

    Выход из системы прост. Просто введите 'halt.' в приглашение к вводу(без кавычек). Сделайте это, а затем перезапустите Prolog.
    Перед тем как вы сможете ознакомиться с возможностями системы, у вас должна быть программа с которой вы собираетесь работать. Используйте предпочитаемый текстовый редактор для ввода программы(например, Sublime - мой любимый, прим. переводчика) из "Пример 2.1". Убедитесь, что дали этому файлу расширение '.pl' - предположим, что вы дали имя 'first.pl'. Для того, чтобы загрузить файл в интерпретатор, введите следующее(не забудьте о точки на конце):

        |  ?- ['first'].

Заметьте, что .pl расширение не указывается - и ничего не забывайте, ни квадратных скобок, ни кавычек, ни точки!

     Интерпретатор SWI-Prolog похож на интерпретатор Hugs в том, что программа состоит из набора определений(считываемых из файла). Интерпретатор Hugs позволяет пользователю вычислять выражение(expression), основываясь на (функциональных) определениях в программе. Таким же образом, интерпретатор SWI-Prolog считывает программу, а затем позволяет пользователю выполнить запрос, основываясь на определениях(фактах и правилах). Запрос "спрашивает) систему, есть ли какие-либо значения, удовлетворяющие определенному предикату(или их комбинации).
    Давайте попробуем посмотреть это на практике.
1. В строке ожидания ввода введите следующее:

        ?-  edge(a, b).

    Когда вы нажмете "ввод", система должна ответить "Yes" и снова вывести ожидание      ввода. Попробуйте еще один ввод, который приведет к ответу "Yes". Всё, что вы вводите - это запросы. Первый спрашивает систему, удовлетворяет ли кортеж (a, b) предикату edge, и, конечно, это так. Попробуйте кортеж, который ложен. Что произойдет, если вы используете имя узла, которого нет ни в одном из фактов? Думаете, будет ошибка? Нет, будет всего лишь ответ 'No'.

2. Теперь введем составные запросы. Что система отвечает на эти запросы?

        ?-  edge(a, b), edge(a, e).
        ?-  edge(a, b), edge(a, c).       

Что вы думаете о назначении ',' ?

3. Теперь попробуем правило. Предикат tedge определяет понятие "путь длиной 2" между двумя узлами. Составьте два запроса, основанных на tedge, которые должны возвращать истину, и два запроса, возвращающих ложь.

4. И теперь очередь финальной демонстрации мощи Prolog'а. Когда идентификатор используется в программе и, при этом, начинается с маленькой буквы, он задает константное значение. Идентификаторы, начинающиеся с большой буквы определяют переменные. Переменные используются в запросах, для того, чтобы найти все значения, которые можно подставить на место переменных, чтобы предикат стал истинным.

    Попробуем следующий запрос.

        ?- edge(a, X).

    Когда вы нажмете "Ввод", система должна вывести значение для X. Если вы нажмете точку с запятой(без нажатия "Ввод"!) - это будет означать, что вы запрашиваете еще одно значение, которое удовлетворяет запросу(если таковое имеется). Если оно есть - оно будет выведено, если нет - будет выведено 'No'. Если вы нажмете "Ввод", а не точку с запятой, новых ответов вы не увидите. Способность Prolog находить все возможные ответы является мощнейшим вычислительным средством.

Теперь, чтобы вы прочувствовали идею, введите следующий запрос и выведите все ответы, посмотрев на их количество.

        ?- edge(X, Y).

5. Prolog содержит некоторые встроенные отношения. Например, отношения <, <=, ==, >=, > могут быть использованы для проверки арифметических отношений на числах. Запрос '1 < 3' успешен, а запрос '3 < 3' вернет 'No'. Поиграйтесь с этим.

Задача № 1

    Опираясь на примеры, приведенные выше, напишите программу на Prolog, которая описывает направленный граф, со следующей структурой(смотрите рисунок). Также включите в программу предикат, который задает отношение "путь длиной 3". Определите его двумя способами: 1) опираясь на отношение edge 2) используя отношение tedge.
    Протестируйте полученное.
P.S. Извините, за скачущую верстку, веб редактор дурацкий на блогере, уже снова поставил Windows Live Writer, новые переводы в нем будут. 

Комментариев нет:

Отправить комментарий