107
МИНИСТЕРСТВО ОБРАЗОВАНИЯ И НАУКИ РОССИЙСКОЙ ФЕДЕРАЦИИ ФЕДЕРАЛЬНОЕ АГЕНТСТВО ПО ОБРАЗОВАНИЮ ГОСУДАРСТВЕННОЕ ОБРАЗОВАТЕЛЬНОЕ УЧРЕЖДЕНИЕ ВЫСШЕГО ПРОФЕССИОНАЛЬНОГО ОБРАЗОВАНИЯ «НОВОСИБИРСКИЙ ГОСУДАРСТВЕННЫЙ ТЕХНИЧЕСКИЙ УНИВЕРСИТЕТ» ___________________________________________________________ ___________ СИСТЕМЫ ИСКУССТВЕННОГО ИНТЕЛЛЕКТА: ПРОГРАММИРОВАНИЕ В СРЕДЕ CLIPS УЧЕБНОЕ ПОСОБИЕ

Учебное пособие по CLIPS

Embed Size (px)

Citation preview

Page 1: Учебное пособие по CLIPS

МИНИСТЕРСТВО ОБРАЗОВАНИЯ И НАУКИ РОССИЙСКОЙ ФЕДЕРАЦИИ

ФЕДЕРАЛЬНОЕ АГЕНТСТВО ПО ОБРАЗОВАНИЮ

ГОСУДАРСТВЕННОЕ ОБРАЗОВАТЕЛЬНОЕ УЧРЕЖДЕНИЕВЫСШЕГО ПРОФЕССИОНАЛЬНОГО ОБРАЗОВАНИЯ

«НОВОСИБИРСКИЙ ГОСУДАРСТВЕННЫЙ ТЕХНИЧЕСКИЙ УНИВЕРСИТЕТ»

______________________________________________________________________

СИСТЕМЫ ИСКУССТВЕННОГО ИНТЕЛЛЕКТА:

ПРОГРАММИРОВАНИЕ В СРЕДЕ CLIPS

УЧЕБНОЕ ПОСОБИЕ

НОВОСИБИРСК

2006

Page 2: Учебное пособие по CLIPS

Рецензент: М.Г. Гриф, доктор техн. наук, профессор

Работа подготовлена на кафедре

автоматизированных систем управления

для студентов IV курса направления 230100

дневного отделения АВТФ

Пушкарева Г.В.

Системы искусственного интеллекта: программирование в среде

CLIPS. Учебное пособие. – Новосибирск: Изд-во НГТУ, 2006. – 73с.

В настоящем пособии изложены теоретические и практические вопросы реализации систем искусственного интеллекта в среде CLIPS. В CLIPS используется оригинальный LISP-подобный язык, ориентированный на разработку экспертных систем (ЭС), и поддерживаются процедурная и объектно-ориентированная парадигмы программирования. Для рассмотрения приведены примеры программ и предложены задания, рекомендованные к выполнению.

Пособие предназначено для студентов IV курса дневного отделения АВТФ, обучающихся по направлению 230100 «Информатика и вычислительная техника» при изучении ими дисциплины «Системы искусственного интеллекта», а также для студентов других смежных направлений, изучающих системы искусственного интеллекта и язык CLIPS.

Новосибирский государственныйтехнический университет, 2006г.

2

Page 3: Учебное пособие по CLIPS

ОГЛАВЛЕНИЕ

Введение 5

1. Знакомство с оболочкой CLIPS. Интерфейс CLIPS

6

1.1. Характеристика инструментального средства разработки

экспертных систем CLIPS 6

1.2. Основные элементы процедурного программирования

в системе CLIPS 7

1.2.1. Простые типы данных 7

1.2.2. Функции для манипулирования данными 9

1.2.3. Конструкции для пополнения базы знаний 10

1.3. Программирование в CLIPS 11

1.3.1. Факты 11

1.3.2. Правила 14

1.3.3. Переменные 16

1.3.4. Дополнительные средства 17

1.4. Интерфейс CLIPS 20

1.5. Задание 22

2. Создание ЭС со стратегией прямого вывода 29

2.1. Пример 1. Разработка ЭС диагностики неисправностей принтера 29

2.1.1. Идентификация проблемы 29

2.1.2. Концептуализация знаний 30

2.1.3. Формализация знаний 32

2.1.4. Реализация системы 34

2.1.5. Тестирование прототипа 36

2.2. Пример 2. Разработка ЭС диагностики неисправностей двигателя 36

2.3. Пример 3. Разработка ЭС организации отдыха 37

2.4. Задание 39

3. Объектно-ориентированное программирование в CLIPS 40

3.1. Объектно-ориентированные средства программирования

3

Page 4: Учебное пособие по CLIPS

в системе CLIPS 40

3.2. Реализация фреймов и наследования в языке CLIPS 44

3.3. Задание 47

4. Решение логических задач в CLIPS 54

4.1. Задача «Правдолюбцы и лжецы» 54

4.2. Анализ проблемы 54

4.3. Онтологический анализ и представление знаний 56

4.4. Разработка правил 60

4.5. Расширение набора правил — работа с составными

высказываниями 63

4.6. Задание 72

Литература 72

4

Page 5: Учебное пособие по CLIPS

ВВЕДЕНИЕ

CLIPS (C Language Integrated Production System) является одним из

распространённых инструментальных средств разработки экспертных систем

(ЭС). Представляя собой логически полную среду, содержащую встроенный

редактор и средства отладки, CLIPS является оболочкой ЭС. CLIPS использует

продукционную модель представления знаний и поэтому содержит три основных

элемента: список фактов, базу знаний (БЗ) и блок вывода.

Принципиальным отличием данной системы от аналогов является то, что она

полностью реализована на языке С. Причём исходные тексты её программ

опубликованы в сети Интернет.

В CLIPS используется оригинальный LISP-подобный язык

программирования, ориентированный на разработку экспертных систем. Кроме

того, CLIPS поддерживает две парадигмы программирования: процедурную и

объектно-ориентированную.

Данное пособие содержит основные теоретические понятия, примеры и

задания по следующим темам:

1) Знакомство с оболочкой CLIPS. Интерфейс CLIPS. Основные элементы

программирования в CLIPS. Позиционные и непозиционные факты. Правила для

представления знаний. Использование шаблонов. Определение функций.

Дополнительные средства написания программ в CLIPS.

2) Создание ЭС со стратегией прямого вывода. Идентификация проблемы.

Извлечение знаний. Концептуализация знаний (разработка поля знаний).

Построение продукционной модели с прямым выводом. Реализация модели

посредством CLIPS. Тестирование проекта.

3) Объектно-ориентированное программирование в CLIPS. Формирование

объекта класса на языке CLPS. Создание обработчиков сообщений классов.

Реализация фреймов и наследования в языке CLIPS.

4) Решение логических задач в CLIPS. Анализ проблемы. Онтологический анализ

и представление знаний. Разработка правил. Расширение набора правил ― работа

5

Page 6: Учебное пособие по CLIPS

с составными высказываниями. Обработка дизъюнктивных и конъюнктивных

утверждений.

1. ЗНАКОМСТВО С ОБОЛОЧКОЙ CLIPS. ИНТЕРФЕЙС CLIPS

1.1. Характеристика инструментального средства

разработки экспертных систем CLIPS

Название языка CLIPS — аббревиатура от С Language Integrated Production

System. Язык был разработан в Центре космических исследований NASA (NASA's

Johnson Space Center) в середине 1980-х годов и во многом сходен с языками,

созданными на базе LISP, в частности OPS5 и ART. Использование С в качестве

языка реализации объясняется тем, что компилятор LISP не поддерживается

частью распространенных платформ, а также сложностью интеграции LISP-кода в

приложения, которые используют отличный от LISP язык программирования.

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

искусственного интеллекта, разработанные на языке С, специалисты из NASA

решили создать такой продукт самостоятельно. Разработанная ими система в

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

возможностям она не уступает множеству гораздо более дорогих коммерческих

продуктов.

Первая версия представляла собой интерпретатор порождающих правил.

Процедурный язык и объектно-ориентированное расширение CLIPS Object-

Oriented Language (COOL) были включены в этот программный продукт только в

1990-х годах. Существующая в настоящее время версия может эксплуатироваться

на платформах UNIX, DOS, Windows и Macintosh. Она является хорошо

документированным общедоступным программным продуктом и доступна по

сети FTP с множества университетских сайтов. Исходный код программного

пакета CLIPS распространяется совершенно свободно и его можно установить на

любой платформе, поддерживающей стандартный компилятор языка С. Однако

лучше пользоваться официальной версией для определенной платформы,

6

Page 7: Учебное пособие по CLIPS

поскольку такие версии оснащены пользовательским интерфейсом, включающим

меню команд и встроенный редактор.

CLIPS включает в себя язык представления порождающих правил и язык

описания процедур.

Основными компонентами языка описания правил являются база фактов

(fact base) и база правил (rule base). На них возлагаются следующие функции:

• база фактов представляет исходное состояние проблемы;

• база правил содержит операторы, которые преобразуют состояние проблемы,

приводя его к решению.

Машина логического вывода CLIPS сопоставляет эти факты и правила и

выясняет, какие из правил можно активизировать. Это выполняется циклически,

причем каждый цикл состоит из трех шагов:

(1) сопоставление фактов и правил;

(2) выбор правила, подлежащего активизации;

(3) выполнение действий, предписанных правилом.

Такой трехшаговый циклический процесс иногда называют «циклом

распознавание-действие».

1.2. Основные элементы процедурного программирования в системе CLIPS

CLIPS предоставляет три основных элемента для написания программ:

• простые типы данных;

• функции для манипулирования данными;

• конструкции для пополнения базы знаний.

1.2.1. Простые типы данных

Для представления информации в CLIPS предусмотрено восемь простых

типов данных:

float, integer, symbol, string, external-address, fact-address, instance-name и instance-

address.

Для представления числовой информации используются типы float и integer,

символьной - symbol и string. Остановимся на рассмотрении этих четырех типов

7

Page 8: Учебное пособие по CLIPS

данных.

При записи числа могут использоваться только цифры (0-9), десятичная

точка (.), знак (+) или (-) и (е) при экспоненциальном представлении. Число

сохраняется либо как целое, либо как действительное. Любое число, состоящее

только из цифр, перед которыми может стоять знак, сохраняется как целое (тип

integer представляется внутри CLIPS как тип языка С long integer). Все остальные

числа сохраняются как действительные (float - С double float). Количество

значащих цифр зависит от аппаратной реализации. В этой же связи могут

возникать ошибки округления.

Как в любом языке программирования, особенную осторожность необходимо

проявлять при сравнении чисел с плавающей точкой, а также при сравнении с

ними целых чисел.

Примеры целых чисел: 237 15 +12 -32

Примеры чисел с плавающей точкой: 237е3 15.09 +12.0 -32.3е-7

Последовательность символов, которая не удовлетворяет числовым типам,

обрабатывается как тип данных symbol.

Тип данных symbol в CLIPS ─ последовательность символов, состоящая из

одного или нескольких любых печатных символов кода ASCII. Как только в

последовательности символов встречается символ-разделитель, symbol

заканчивается. Следующие символы служат разделителями: любой непечатный

ASCII символ (включая пробел, символ табуляции, CR, LF), двойные кавычки,

«(», «)», «&», «|», «<», «~», «;». Символы-разделители не могут включаться в

symbol за исключением символа «<», который может быть первым символом в

symbol. Кроме того, symbol не может начинаться с символа «?» или

последовательности символов «$?», поскольку эти символы зарезервированы для

переменных. Заметим, что CLIPS различает регистр символов. Ниже приведены

примеры выражений символьного типа:

foo Hello B76-HI bad_value 127А 742-42-42 @+=-% Search

Тип данных string - это последовательность символов, состоящая из нуля и

более печатных символов и заключенная в двойные кавычки. Если внутри строки

8

Page 9: Учебное пособие по CLIPS

встречаются двойные кавычки, то перед ними необходимо поместить символ (\).

То же справедливо и для самого (\). Несколько примеров: «foo» «a and b» «I

number» «a\»quote»

Отметим, что строка «abcd» не тоже самое, что abcd. Они содержат одина-

ковые наборы символов, но являются экземплярами различного типа.

1.2.2. Функции для манипулирования данными

Под функцией в CLIPS понимается фрагмент исполняемого кода, с которым

связано уникальное имя и который возвращает полезное значение или имеет

полезный побочный эффект (например, вывод информации на экран).

Существует несколько типов функций. Пользовательские и системные фун-

кции - это фрагменты кода, написанные на внешних языках (например, на С) и

связанные со средой CLIPS. Системными называются те функции, которые были

определены изначально внутри среды CLIPS. Пользовательскими называются

функции, которые были определены вне CLIPS.

Хотя CLIPS и не ориентирована на численные вычисления, в ней предусмот-

рен ряд стандартных арифметических и математических функций (см. табл.1).

Таблица 1

Стандартные арифметические и математические функции

+ Сложение

- Вычитание

* Умножение

/ Деление

** Возведение в степень

Abs Определение абсолютного значения

Sqrt Вычисление квадратного корня

Mod Нахождение остатка от деления

Min Нахождение минимума

Max Нахождение максимума

9

Page 10: Учебное пособие по CLIPS

Конструкция deffunction позволяет пользователю определять новые функции

непосредственно в среде CLIPS с использованием синтаксиса CLIPS. Функции,

определенные таким образом, выглядят и работают подобно остальным фун-

кциям, однако они выполняются не напрямую, а интерпретируются средой CLIPS.

Вызовы функций в CLIPS имеют префиксную форму: аргументы функции могут

стоять только после ее названия. Вызов функции начинается с открывающейся

скобки, за которой следует имя функции, затем идут аргументы, каждый из

которых отделен одним или несколькими пробелами. Аргументами функции

могут быть данные простых типов, переменные или вызовы других функций. В

конце вызова ставится закрывающаяся скобка. Ниже приведены примеры вызовов

функций:

(+ 3 4 5)

(* 5 6.0 2)

(+3 (* 8 9) 4)

(* 8 (+ 3 (* 2 3 4) 9) (* 3 4))

1.2.3. Конструкции для пополнения базы знаний

В CLIPS существует несколько описывающих конструкций:

defmodule, defrule, deffacts, deftemplate, defglobal, deffunction, defclass, definstances,

defmessage-handler, defgeneric.

При записи все они заключаются в скобки. Определение конструкции отли-

чается от вызова функции главным образом по производимому эффекту. Обычно

вызов функции оставляет состояние среды CLIPS без изменений (за рядом

исключений, когда речь идет о функциях сброса, очистки, открытия файла и т.п.).

Определение конструкции, напротив, в точности направлено на изменение

состояния среды путем внесения изменений в базу знаний CLIPS. В отличие от

функций конструкции никогда не возвращают значений.

Все конструкции (за исключением defglobal) позволяют размещать ком-

ментарии сразу вслед за именем конструкции. Кроме того, комментарии могут

вставляться в код CLIPS при помощи точки с запятой (;). Все, что следует за (;) до

10

Page 11: Учебное пособие по CLIPS

конца строки, будет игнорироваться CLIPS. Если (;) стоит первым символом в

строке, то вся строка считается комментарием.

1.3. Программирование в CLIPS

1.3.1. Факты

Факты являются одной из основных форм представления информации в

системе CLIPS. Каждый факт представляет фрагмент информации, который был

помещен в текущий список фактов, называемый fact-list. Факт представляет собой

основную единицу данных, используемую правилами.

Количество фактов в списке и объем информации, который может быть со-

хранен в факте, ограничивается только размером памяти компьютера. Если при

добавлении нового факта к списку обнаруживается, что он полностью совпадает с

одним из уже включенных в список фактов, то эта операция игнорируется (хотя

такое поведение можно изменить).

Факт может описываться индексом или адресом. Всякий раз, когда факт

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

Индексы фактов начинаются с нуля и для каждого нового или измененного факта

увеличиваются на единицу. Каждый раз после выполнения команд reset и clear

выделение индексов начинается с нуля. Факт также может задаваться при помощи

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

значения команд, которые возвращают в качестве результата адрес факта (таких

как assert, modify и duplicate), или путем связывания переменной с адресом факта

в левой части правила (см. далее).

Идентификатор факта - это короткая запись для отображения факта на

экране. Она состоит из символа f и записанного через тире индекса факта. На-

пример, запись f-10 служит для обозначения факта с индексом 10. Существует два

формата представления фактов: позиционный и непозиционный.

Позиционные факты

Позиционные факты состоят из выражения символьного типа, за которым

следует последовательность (возможно, пустая) из полей, разделенных пробе-

11

Page 12: Учебное пособие по CLIPS

лами. Вся запись заключается в скобки. Обычно первое поле определяет «отно-

шение», которое применяется к оставшимся полям. Например:

(the pump is on)

(altitude is 10000 feet)

(grocery_list bread milk eggs)

Поля в позиционных фактах могут быть любого простого типа (за

исключением первого поля, которое всегда должно быть типа symbol), на порядок

полей также не накладывается никаких ограничений. Следующие символьные

выражения зарезервированы и не должны использоваться как первое поле любого

факта (позиционного или нет): test, and, or, not, declare, logical, object, exists и

forall.

Непозиционные факты

Для того чтобы обратиться к информации, содержащейся в позиционном

факте, пользователь должен знать не только какие данные содержатся в факте, но

и то, в каком поле они хранятся. Непозиционные (шаблонные) факты дают

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

каждому из полей факта. Для задания шаблона, который затем может

использоваться при доступе к полям по именам, используется конструкция

deftemplate. Эта конструкция подобна структуре или записи в языках

программирования С и Паскаль.

Конструкция deftemplate позволяет наряду с определением именованных

полей, или слотов, вводить имя шаблона. В отличие от позиционных фактов

слоты шаблонного факта могут быть ограничены по типу, значению, числовому

диапазону. Кроме того, для любого слота можно определить значение по

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

следует имя слота, определения поля (могут отсутствовать), и закрывающейся

скобки. Заметим, что слоты не могут использоваться в позиционных фактах, так

же как позиционные поля не могут использоваться в шаблонных фактах. Общая

структура конструкции deftemplate такова:

(deftemplate <name>

12

Page 13: Учебное пособие по CLIPS

(slot-1)

(slot-2)

• • •

(slot-N))

Далее приведен пример шаблона с заданными для слотов значениями по

умолчанию:

(deftemplate prospect

(slot name (default ?DERIVE))

(slot assets (default rich))

(slot age (default 80)))

Шаблонные факты отличаются от позиционных по первому полю в факте.

Первое поле всех фактов должно быть типа symbol, но если это символьное

выражение соответствует имени шаблона, то этот факт - шаблонный. За первым

полем шаблонного факта следует список из нуля или более слотов. Как и

позиционные, шаблонные факты заключаются в скобки. Далее приведено не-

сколько примеров шаблонных фактов:

(client (name “Joe Brown”) (id X9345A))

(point-mass (x-velocity 100) (y-velocity -200))

(class (teacher “Martha Jones”) (#-students 30) (room “37A”))

(grocery-list (#-of-items 3) (items bread milk eggs))

Заметим, что порядок следования слотов в шаблонном факте не важен.

Манипуляции над фактами

Факты могут добавляться к списку фактов (с помощью команды assert),

удаляться из него (с помощью команды retract), изменяться (с помощью команды

modify) и дублироваться (с помощью команды duplicate) самим пользователем

или программой. Например:

(assert (light green))

Кроме того, конструкция deffacts позволяет определить множество исходных

или априорных знаний в виде набора фактов. Например:

(deffacts today

13

Page 14: Учебное пособие по CLIPS

(status walking)

(weather is warm))

Конструкция deffacts начинается с команды deffacts, затем приводится имя

списка фактов (в нашем примере ─ today), а за ним следуют элементы списка,

причем их количество не ограничивается. Этот список фактов можно затем

удалить из базы командой undeffacts. Например:

(undeffacts today)

Когда производится сброс состояния среды CLIPS (с помощью команды

reset) все факты, описанные в конструкции deffacts, добавляются к списку фактов.

Кроме того, по этой команде в список фактов заносится исходный факт (initial-

fact). Этот факт включается в список фактов всегда с идентификатором f-0. Его

назначение будет рассмотрено в следующем пункте.

1.3.2. Правила

Одним из основных методов представления знаний в CLIPS являются

правила. Правила используются для представления эвристик, определяющих ряд

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

экспертной системы определяет совокупность правил, которые используются

совместно для решения проблемы. Правило состоит из двух частей: антицедента

(условия), который является аналогом условия в if-then операторе и записывается

слева, и консеквента (заключения), который является аналогом then части этого

оператора и записывается справа.

Левая часть правила представляет собой ряд условий (условных элементов),

которые должны выполняться, чтобы правило было применимо. В CLIPS принято

считать, что условие выполняется, если соответствующий ему факт присутствует

в списке фактов. Одним из типов условных элементов может быть образец.

Образцы состоят из набора ограничений, которые используются для описания

того, какие факты удовлетворяют условию, определяемому образцом. Процесс

сопоставления фактов и образцов выполняется блоком вывода CLIPS, который

автоматически сопоставляет образцы, исходя из текущего состояния списка

фактов, и определяет, какие из правил являются применимыми. Если все условия

14

Page 15: Учебное пособие по CLIPS

правила выполняются, то оно активируется и помещается в список

активированных правил.

Если левая часть правила пуста, то для его активации необходимо наличие в

списке фактов исходного факта (initial-fact). Такие безусловные правила часто

используются для того, чтобы инициировать работу программы. Поэтому перед

запуском таких программ необходимо произвести сброс состояния среды CLIPS.

Правая часть правила представляет собой совокупность действий, которые

должны быть выполнены, если правило применимо. Действия, описанные в при-

менимых правилах, выполняются тогда, когда блок вывода CLIPS получает ко-

манду начать выполнение применимых правил. Если существует множество при-

менимых правил, то для того, чтобы выбрать правило, действия которого должны

быть выполнены, блок вывода использует стратегию разрешения конфликтов.

Действия, описанные в выбранном правиле, выполняются (при этом список

применимых правил может измениться), а затем блок вывода выбирает другое

правило и т.д. Этот процесс продолжается до тех пор, пока не остается ни одного

применимого правила, т.е. пока список активированных правил не окажется пуст.

Во многом правила похожи на операторы типа if-then процедурных языков

программирования. Однако условие if-then оператора в процедурном языке

проверяется только тогда, когда программа передает ему управление. С прави-

лами ситуация иная. Блок вывода постоянно отслеживает все правила, условия

которых выполняются, и, таким образом, правило может быть выполнено в любой

момент, как только оно становится применимым. В этом смысле правила подобны

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

языке Ада).

Для определения правил используется конструкция defrulе:

(defrule rule_name “optional_comment”

(patten_1)

(patten_2)

(patten_N)

15

Page 16: Учебное пособие по CLIPS

=>

(action_1)

(action_2)

(action_M))

Например:

(defrule take-a-vacation

(work done)

(money plenty)

(reservations made)

=>

(printout t “Let's go!” crlf))

1.3.3. Переменные

Как и в других языках программирования, в CLIPS для хранения значений

используются переменные. В отличие от фактов, которые являются статическими,

или неизменными, содержание переменной динамично и изменяется по мере того,

как изменяется присвоенное ей значение.

Идентификатор переменной всегда начинается с вопросительного знака, за

которым следует ее имя. В общем случае формат переменной выглядит следу-

ющим образом:

?<variable-name>

Примеры переменных:

?x ?sensor ?noun ?color

Перед использованием переменной ей необходимо присвоить значение. Все

переменные, кроме глобальных, считаются локальными и могут использоваться

только в рамках описания конструкции. К этим локальным переменным можно

обращаться внутри описания, но они не определены вне него.

Чаще всего переменные описываются и получают значения в левой части

правила. Например:

(defrule make-quack

16

Page 17: Учебное пособие по CLIPS

(duck-sound ?sound)

=>

(assert (sound-is ?sound)))

Получив значение, переменная сохраняет его неизменным при использова-

нии как в левой, так и в правой части правила, если только это значение не

изменяется в правой части при помощи функции bind.

(defrule addition

(numbers ?x ?y)

=>

(assert (answer (+ ?x ?y)))

(bind ?answer (+ ?x ?y))

(printout t “answer is ” ?answer crlf))

Кроме значения самого факта, переменной может быть присвоено значение

адреса факта. Это может оказаться удобным при необходимости манипулировать

фактами непосредственно из правила. Для такого присвоения используется

комбинация «<–». Следующий пример иллюстрирует присвоение переменной

значения адреса факта и ее последующее использование:

(defrule get-married

?duck <– (bachelor Dopey)

=>

(retract ?duck))

Для определения глобальных переменных, которые видны всюду в среде

CLIPS, используется конструкция defglobal. К глобальной переменной можно

обратиться в любом месте, и ее значение остается независимым от других кон-

струкций. Глобальные переменные CLIPS подобны глобальным переменном в

процедурных языках программирования, но они значительно слабее типизиро-

ваны (на них не налагается ограничения хранения данных только одного типа).

1.3.4. Дополнительные средства

CLIPS предоставляет ряд дополнительных средств, необходимых при на-

писании программ. Основными из них являются:

17

Page 18: Учебное пособие по CLIPS

ограничения на значения полей;

оператор проверки условия test;

использование функций в правилах;

использование процедурных знаний.

Рассмотрим каждое из этих средств по очереди.

Ограничения на значения полей

Использование ограничений на значения полей позволяет ограничить зна-

чения, принимаемые образцами в левой части правила.

Рассмотрим три вида ограничений: ~, | и &.

Ограничение первого типа действует на следующее прямо за ним значение и

говорит о том, что поле не может принимать это значение. Например:

(defrule walk

(light ~green)

=>

(printout t “Don't walk” crlf))

Ограничение второго типа указывает на то, что поле может принимать одно

из следующих значений. Например:

(defrule cautious

(light yellow | blinking-yellow)

=>

(printout t “Be cautious” crlf))

Ограничение третьего типа используется только вместе с ограничениями

первых двух типов и указывает на то, что должны удовлетворяться оба соеди-

няемых при его помощи ограничения. Например:

(defrule cautious

(light ?color & yellow | blinking-yellow)

=>

(printout t “Be cautious because light is ” ?color crlf))

Оператор проверки условия test

Оператор проверки условия test представляет собой мощное средство, при

18

Page 19: Учебное пособие по CLIPS

помощи которого можно сравнивать числа, переменные и строки в левой части

правила. Он записывается точно так же, как и образцы. Правило может

выполниться только тогда, когда наряду с совпадением всех образцов,

записанных в левой части правила, справедливо и условие, описываемое в test.

Функция test имеет следующий синтаксис:

(test (аргумент_сравнения аргумент_1 аргумент_2))

где аргумент_сравнения - это тот параметр, по которому сравниваются два

следующих аргумента. В CLIPS существует ряд предопределенных аргументов

сравнения (см. табл. 2).

Таблица 2

Предопределенные аргументы сравнения

eq Равно (сравнивает тип и значение)

neq Не равно

= Равно (сравнивает только значение)

<> Не равно

>= Больше или равно

> Больше

<= Меньше или равно

< Меньше

Все предопределенные аргументы сравнения, кроме eq и neq, используются

только для сравнения чисел. При интерпретации выражения сравнения считается

что аргумент_1 стоит слева от аргумента_сравнения, а аргумент_2 ― справа.

Использование функций в правилах

Функции могут использоваться и в левой, и в правой части правила. Напри-

мер:

(defrule addition

(numbers ?x ?y)

=>

(assert (answer (+ ?х ?у))))

19

Page 20: Учебное пособие по CLIPS

При использовании функции в левой части правила перед ней должен стоять

знак «=», показывающий CLIPS, что следующее выражение необходимо

вычислить, а не использовать буквально. Например:

(defrule addition

(numbers ?x ?y)

(stock ?ID = (sqrt (+ (** ?x 2) (** ?у 2))))

=>

(printout t “stock ID = ” ?ID crlf))

Использование процедурных знаний

CLIPS поддерживает также процедурную парадигму представления знаний,

подобную принятой в обычных языках программирования (С, Паскаль). Кон-

струкция deffunction позволяет пользователю определять новые функции. Эти

новые функции могут вызываться точно так же, как и встроенные функции

CLIPS. Конструкция defmodule позволяет разбивать базу знаний на части.

1.4. Интерфейс CLIPS

Оболочка ЭС CLIPS может работать в нескольких режимах:

1) интерактивно, с использованием простого текстового интерфейса командной

строки;

2) интерактивно, с использованием GUI-интерфейса;

3) как ЭС, интегрированная в другие приложения.

Основным методом взаимодействия пользователя с CLIPS является ввод

команд с командной строки CLIPS. После появления на экране подсказки

CLIPS>

пользователь может ввести команду.

Командами могут быть вызовы функций, конструкции, глобальные пере-

менные или константы. Если ввести вызов функции, вычисляется значение этой

функции и на экран выводится результат. Как уже отмечалось, вызовы функций в

CLIPS имеют префиксную форму, т.е. аргументы функции могут стоять только

после ее названия. Если ввести определение, то будет создана конструкция

20

Page 21: Учебное пособие по CLIPS

соответствующего типа. В ответ на ввод глобальной переменной на экран будет

выведено ее значение. За вводом константы последует вывод ее на экран (что

вряд ли принесет много пользы). Например:

CLIPS> (+ 3 4)

7

CLIPS> (defglobal ?*x* = 3)

CLIPS> ?*x*

3

CLIPS> red

red

CLIPS>

В приведенном примере сначала была вызвана функция сложения с аргу-

ментами 3 и 4, которая вернула результат 7. Затем была определена глобальная

переменная ?*х*, и ей было присвоено значение 3. Далее переменная ?*х* была

введена с командной строки, и было возвращено ее значение 3. И наконец, была

введена и тут же возвращена константа red.

Стандартная процедура использования интерфейса командной строки выг-

лядит следующим образом:

1) создать и редактировать базу знаний при помощи любого текстового редактора;

2) сохранить базу знаний в одном или нескольких текстовых файлах;

3) выйти из редактора и запустить CLIPS;

4) загрузить базу знаний в CLIPS.

Рассмотрим пример 1.

1) Создадим при помощи любого текстового редактора (например, встроенного

редактора CLIPS или Notepad) текстовый документ такого содержания:

(defrule startup

=>

(assert (light green)))

(defrule one

(light green)

21

Page 22: Учебное пособие по CLIPS

=>

(printout t “Go !!!” crlf))

2) Сохраним его в файле под любым именем (например, TEST.CLP).

3) Запустим CLIPS (на экране появится главное диалоговое окно CLIPS).

4) Теперь для загрузки правил startup и one в базу знаний CLIPS воспользуемся

командой Load меню File.

5) Запуск программы осуществляется последовательным выполнением команд

(reset) и (run).

1.5. Задание

1. Реализовать пример 1, представленный в предыдущем пункте.

2. Реализовать пример 2, представленный в виде следующей

криптоарифметической задачи.

Постановка задачи

Термин «криптоарифметическая» означает использование цифр,

зашифрованных буквами, и соответственно чисел, зашифрованных словами.

Задача состоит в том, чтобы найти, какие цифры нужно подставить вместо букв,

чтобы представленные арифметические операции над расшифрованными числами

давали верный результат. Такая задача рассматривается во многих классических

работах по искусственному интеллекту.

Написать программу для решения следующего ребуса:

GERALD

+ DONALD

---------------

ROBERT

В словах GERALD, DONALD и ROBERT вместо букв необходимо поставить

цифры таким образом, чтобы получилось математически правильное выражение.

Причем разным буквам должны соответствовать разные цифры.

Алгоритм решения

22

Page 23: Учебное пособие по CLIPS

Рассмотрим первые разряды всех трех чисел. Считаем, что первый разряд -

это единицы, второй разряд - это десятки, третий - сотни и т.д. Очевидно, что

нахождение множества пар (буква - цифра), входящих в решение задачи, должно

удовлетворять условию:

(((D+D) mod 10) = T) & (D ? T), (1)

где символ ? обозначает отношение неравенства значений переменных.

Теперь рассмотрим второй разряд вместе с первым. Необходимо подобрать

такие числа L и R, чтобы остаток от деления суммы (L*10 + L*10 + D + D) на 100

был равен (R*10 + Т). И при этом L и R не были равны между собой и не были

равны D и Т. Т.е. среди множества пар (буква - цифра), удовлетворяющих

первому условию, необходимо найти такие, что:

(((L*10 + L*10 + D + D) mod 100) = (R*10 + T)) & (D ? T ? L ? R). (2)

Продолжая действовать подобным образом, можно выписать конечное ус-

ловие, которому должны удовлетворять пары (буква - цифра), входящие в ре-

шение данной задачи.

Решение задачи в CLIPS

Итак, сформулируем описанный выше подход к решению в терминах CLIPS.

Представим комбинации из одной буквы и одной цифры в виде фактов:

(combination D 0), (combination D 1), (combination A 1) и т.д.

Для начала составим правило для нахождения комбинаций (буква - цифра),

удовлетворяющих условию (1):

(defrule find_solution

(combination D ?d)

(combination Т ?t&~?d)

(test (= (mod (+ ?d ?d) 10) ?t) )

=>

(printout t “A Solution is:” t t)

(printout t “ D = ” ?d t)

(printout t “ T = ” ?t t))

23

Page 24: Учебное пособие по CLIPS

Данное правило выполнимо только в том случае, если в списке фактов су-

ществуют факты, удовлетворяющие условиям:

1) (combination D ?d) - все факты, в которых в первой и во второй позициях

стоят «combination» и «D» соответственно. А в третьей позиции любое значение,

это значение присваивается переменной ?d.

2) (combination T ?t&~?d) - все факты, в которых в первой и во второй позициях

стоят «combination» и «Т» соответственно. А в третьей позиции любое значение,

только не то, которое было присвоено переменной ?d, это значение присваивается

переменной ?t. Знак & означает логическое AND, а знак ~ ― логическое NOT.

Выражение ?t&~?d означает, что переменная ?t может принимать значение, не

равное значению переменной ?d.

3) (test (= (mod (+ ?d ?d) 10) ?t)) - это условие проверяет на равенство два

выражения (mod (+ ?d ?d) 10) и (?t) (см. условие (1)).

Команда (printout t “A Solution is:” t t) выводит на экран информацию. Ин-

формация, которую необходимо вывести на экран, указывается в полях, разде-

ленных пробелами, после команды. Чтобы вывести текст, его необходимо зак-

лючить в кавычки, а перед кавычками поставить букву t. Эта буква указывает, что

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

Если после буквы t нет текста в кавычках, то происходит перевод курсора на

новую строку. Перевести курсор на новую строку можно параметром crlf. Он

указывается без кавычек. Чтобы вывести значение переменной, надо просто

указать имя переменной. Например:

(printout t “ Т = ” ?t t)

сначала выводит текст Т=, затем значение переменной ?t и затем переводит

курсор на новую строку.

Последнее приведенное правило позволяет найти все комбинации (буква -

цифра), удовлетворяющие условию для первых разрядов трех чисел. По аналогии

с этим правилом составим конечное правило для нахождения решения:

(defrule find_solution

(combination D ?d&~0)

24

Page 25: Учебное пособие по CLIPS

(combination T ?t&~?d)

(test (= (mod (+ ?d ?d) 10) ?t))

(combination L ?l&~?d&~?t)

(combination R ?r&~?d&~?t&~?l)

(test (= (mod (+ ?d ?d (* 10 ?l) (* 10 ?l)) 100) (+ (* 10 ?r) ?t)))

(combination A ?a&~?d&~?t&~?l&~?r)

(combination E ?e&~?d&~?t&~?l&~?r&~?a)

(test (= (mod (+ ?d ?d (* 10 ?l) (* 10 ?l) (* 100 ?a) (* 100 ?a)) 1000) (+ (* 100 ?e)

(* 10 ?r) ?t)))

(combination N ?n&~?d&~?t&~?l&~?r&~?a&~?e)

(combination B ?b&~?d&~?t&~?l&~?r&~?a&~?e&~?n)

(test (= (mod (+ ?d ?d (* 10 ?l) (* 10 ?l) (* 100 ?a) (* 100 ?a) (* 1000 ?r) (* 1000 ?

n)) 10000) (+ (* 1000 ?b) (* 100 ?e) (* 10 ?r) ?t)))

(combination O ?o&~?d&~?t&~?l&~?r&~?a&~?e&~?n&~?b)

(test (= (mod (+ ?d ?d (* 10 ?l) (* 10 ?l) (* 100 ?a) (* 100 ?a) (* 1000 ?r) (* 1000 ?

n) (* 10000 ?e) (* 10000 ?o)) 100000) (+ (* 10000 ?o) (* 1000 ?b) (* 100 ?e) (* 10 ?

r) ?t)))

(combination G ?g&~?d&~?t&~?l&~?r&~?a&~?e&~?n&~?b&~?o&~0)

(test (= (+ ?d ?d (* 10 ?l) (* 10 ?l) (* 100 ?a) (* 100 ?a) (* 1000 ?r) (* 1000 ?n) (*

10000 ?e) (* 10000 ?o) (* 100000 ?g) (* 100000 ?d)) (+ (* 100000 ?r) (* 10000 ?o) (*

1000 ?b) (* 100 ?e) (* 10 ?r) ?t)))

=>

(printout t “A Solution is:” t t) (printout t “ G = “ ?g t) (printout t “ E = “ ?e t)

(printout t “ R = “ ?r t)

(printout t “ A = “ ?a t) (printout t “ L = “ ?l t) (printout t “ D = “ ?d t) (printout t

“ O = “ ?o t)

(printout t “ N = “ ?n t) (printout t “ B = “ ?b t) (printout t “ T = “ ?t t) (printout t t)

(printout t “ ” ?g ?e ?r ?a ?l ?d t)

(printout t “ + ” ?d ?o ?n ?a ?l ?d t)

(printout t “ ---------” t)

25

Page 26: Учебное пособие по CLIPS

(printout t “ = ” ?r ?o ?b ?e ?r ?t t t))

Теперь для поиска решения остается занести факты, соответствующие ком-

бинациям из одной буквы и одной цифры, в список фактов. Это можно сделать

командой assert.

(assert (combination D 0)

(combination D 1)

(combination A 1)

(combination L 9)

...)

Однако, т.к. количество фактов равно 100, лучше поступить по-другому.

Сопоставим буквам и цифрам следующие факты:

(number 0), (number 1), (number 2), ..., (number 9);

(letter G), (letter E), (letter R), (letter A), (letter L), (letter D), (letter O),(letter N), (letter

B), (letter T).

Составим правило, по которому в список фактов будут заноситься факты,

соответствующие комбинациям из одной буквы и одной цифры.

(defrule generate_combination

(number ?x)

(letter ?y)

=>

(assert (combination ?y ?x)))

Согласно данному правилу, если в списке фактов присутствуют факты, име-

ющие вид (number ?x), (letter ?y), где вместо переменных стоят вполне конкретные

значения, в список фактов добавляется еще один факт ― (combination ?y ?x), в

котором вместо переменных стоят значения из фактов.

И наконец, составим правило, по которому, во-первых, на экран будет вы-

водиться условие задачи, а во-вторых, в список фактов будут заноситься факты,

соответствующие буквам и цифрам. Т.к. это правило должно выполняться всегда,

его условная часть будет пустой.

(defrule startup

26

Page 27: Учебное пособие по CLIPS

=>

(printout t t “The problem is:” t t)

(printout t “ GERALD” t) (printout t “ + DONALD” t)

(printout t “ ---------------” t) (printout t “ = ROBERT” t t)

(assert (number 0) (number 1) (number 2) (number 3) (number 4) (number 5)

(number 6) (number 7) (number 8) (number 9) (letter G) (letter E) (letter R) (letter A)

(letter L) (letter D) (letter O) (letter N) (letter B) (letter T)))

Таким образом, наша программа состоит из трех правил: startup,

generate_combination и find_solution. Первое из них выводит на экран условие

задачи и добавляет к списку фактов факты, соответствующие отдельным буквам и

цифрам. Второе правило, используя факты, введенные в список фактов первым

правилом, заносит в список фактов факты, которые представляют собой

всевозможные комбинации из десяти цифр и десяти букв. Третье правило

позволяет найти среди этих фактов те, которые удовлетворяют условию задачи, и

выводит на экран полученное решение.

Порядок реализации задачи в CLIPS

1) Запуск CLIPS.

Для сохранения протокола работы программы, а также полученного ответа в

текстовом файле необходимо сразу после запуска CLIPS выполнить команду

(Turn Dribble On) в меню File. В появившемся диалоговом окне нужно ввести имя

файла, в который будет сохраняться содержимое главного окна CLIPS.

После получения ответа, перед очисткой CLIPS выполните команду (Turn

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

диалогового окна CLIPS, будет закрыт.

2) Ввод программы с использованием встроенного редактора CLIPS.

3) Сохранение файла программы под именем Wordgame.clp.

4) Загрузка и запуск программы.

Загрузка в БЗ CLIPS содержимого файла Wordgame.clp осуществляется

посредством пункта Load меню File.

27

Page 28: Учебное пособие по CLIPS

Данный файл содержит три правила. Правило startup не содержало условий.

CLIPS активизирует правило без условий при наличии в списке фактов (initial-

fact) с идентификатором f-0. Занести этот факт в список фактов можно с помощью

команды (reset).

Данная команда удаляет существующие факты из списка фактов, включает в

список фактов исходный факт (initial-fact) и все факты, описанные в конструкциях

(deffacts). Команда (reset) не затрагивает правила, а лишь очищает список

активированных правил (диалоговое окно Agenda).

Чтобы запустить программу, необходимо выполнить команду (run).

После этой команды CLIPS начнёт выполнять все правила, которые нахо-

дятся в списке активизированных правил. Выполнение программы останавли-

вается либо когда в списке правил больше не останется ни одного активного

правила, либо по прерыванию от пользователя, комбинацией клавиш (Ctrl+C).

Если после выполнения программы необходимо очистить базу знаний CLIPS,

а также убрать все факты из списка фактов, т.е. привести CLIPS в начальное

состояние, то необходимо воспользоваться командой (clear).

Команда (clear) осуществляет очистку CLIPS от всех правил и фактов. В

отличие от команды (reset), которая удаляет только все факты из списка фактов и

очищает список активированных правил.

3. Решить следующие криптоарифметические задачи, используя алгоритм

решения задачи предыдущего пункта:

SEND CROSS + MORE + ROADS ------------ ------------- MONEY DANGER

4. Оформить отчёт о выполнении задания 1.5, включив в него тексты

программ пунктов 1, 2 и 3 данного задания, а также результаты работы системы

CLIPS.

28

Page 29: Учебное пособие по CLIPS

2. СОЗДАНИЕ ЭС СО СТРАТЕГИЕЙ ПРЯМОГО ВЫВОДА

2.1. Пример 1. Разработка ЭС диагностики неисправностей принтера.

2.1.1. Идентификация проблемы

Цель: разработать простую и удобную в эксплуатации экспертную систему

диагностики неисправностей принтера.

Постановка задачи: необходимо реализовать блок логического вывода

посредством CLIPS и протестировать его на различных наборах фактов.

Описание предметной области

Данная экспертная система разработана для диагностики неполадок

принтеров. В настоящее время наиболее известными производителями принтеров

являются такие компании, как HP, Canon, Lexmark, Epson.

Существует несколько видов принтеров: матричные, струйные и лазерные.

Матричные принтеры имеют приемлемое качество печати, невысокую цену

расходных материалов и бумаги, да и самих устройств. Но они создают много

шума, а это немаловажный фактор при выборе принтера. Матричные принтеры

почти вытеснены с рынка струйными и лазерными принтерами. Струйные

принтеры работают практически бесшумно. При печати высокого качества

скорость вывода составляет обычно 2-3, хотя максимальные значения могут

достигать даже 7 страниц в минуту. В лазерных принтерах используется

электрографический способ создания изображения - примерно такой же, как и в

ксероксах. Они имеют высокую скорость печати.

Все принтеры имеют примерно одни и те же неполадки, возникающие в

процессе эксплуатации. Их можно разделить на следующие группы:

1) проблемы качества печати (горизонтальные полосы, вертикальные

полосы, неправильные цвета и т. д.)

2) неправильные отпечатки (неправильные символы, отпечатка чистых

страниц и т.д.)

3) неправильная подача бумаги (бумага не подается, подача нескольких

страниц за один раз, бумага заклинивается и т.д.).

29

Page 30: Учебное пособие по CLIPS

В основу неполадок, диагностируемых разрабатываемой экспертной

системой, были положены неполадки, возникающие в процессе эксплуатации

принтеров Epson Stylus C60.

Источники знаний

При разработке фактов и правил создаваемой экспертной системы были

использованы данные программы ES C60 Problem Solver, поставляемой вместе с

драйвером принтера Epson Stylus C60, а также данные, содержащиеся на Web-

сайте технической поддержки Epson http://support.epson.ru/ и сайте Московского

представительства Epson http://www.epson.ru/.

2.1.2. Концептуализация знаний

Поле знаний состоит из концептуальной и функциональной структур

предметной области.

Концептуальная структура служит для описания ее объектов и

отношений между ними (см. табл.3 и табл. 4).

Таблица 3

Входные факторы

неполадки принтера

проблемы качества печати

неправильные отпечатки неправильная подача бумаги

1) горизонтальные полосы 1) неправильные символы 1) бумага не подается

2) вертикальные полосы 2) неправильные поля 2) подача нескольких

страниц за один раз

3) пропуск цветов 3) отпечатка чистых

страниц

3) бумага заклинивается

4) неправильные цвета 4) отпечаток смазан 4) бумага мнется или не

выводится полностью

5) размытый отпечаток

30

Page 31: Учебное пособие по CLIPS

Таблица 4

Выходные факторы

устранение неполадок

оборудование материалы программное обеспечение

1) чистка печатной

головки

1) правильная загрузка

бумаги

1) установка необходимых

драйверов

2) выравнивание

печатной головки

2) правильная установка

чернил

2) правильная установка

параметров страницы

Функциональная структура отражает модель рассуждения в процессе

принятия решений. Она может быть представлена в виде таблицы (если модель

двухуровневая) или графа (многоуровневая модель). В данном примере

функциональная модель – двухуровневая (см. табл.5).

Таблица 5

Функциональная структура

Входные факторы Выходные факторы

проблемы качества печати

неправильные отпечатки

неправильная подача бумаги

оборудование материалы программное обеспечение

горизонталь-ные полосы

выравнивание печатной головки

вертикальные полосы

правильная установка чернил

пропуск цветов правильная загрузка бумаги

неправильные цвета

чистка печатной головки

размытый отпечаток

установка необходимых драйверов

31

Page 32: Учебное пособие по CLIPS

Продолжение табл. 5

неправильные символы

установка необходимых драйверов

неправильные поля

правильность установки параметровстраницы

отпечатка чистых страниц

установка необходимых драйверов

отпечаток смазан

правильная загрузка бумаги

бумага не подается

выравнивание печатной головки

подача нескольких страниц за один раз

правильная загрузка бумаги

бумага заклинивается

правильная загрузка бумаги

бумага мнется или не выводится полностью

правильная загрузка бумаги

2.1.3. Формализация знаний

Формализация — представление знаний в виде системы продукций с прямым

выводом.

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

представить знания в виде предложений типа: «если (условие), то (действие)».

Под условием или антецедентом понимается некоторое предложение - образец, по

которому осуществляется поиск в базе знаний, а под действием (консеквентом)

понимается действие, выполняемое при успешном исходе поиска. Эти действия

могут быть промежуточными, выступающими далее как условие, или целевыми,

завершающими работу системы. При использовании продукционной модели БЗ

32

Page 33: Учебное пособие по CLIPS

состоит из набора правил. Программа, управляющая перебором правил

называется машиной вывода.

Чаще всего вывод на такой БЗ бывает прямой (от данных к поиску цели) или

обратный (от цели для ее подтверждения к данным). Данные - это исходные

факты, хранящиеся в базе фактов (БД), на основе которой запускается машина

вывода или интерпретатор правил, перебирающий правила из продукционной БЗ.

Продукционная модель чаще всего применяется в промышленных ЭС, она

привлекает разработчиков своей наглядностью, модульностью, легкостью

внесения дополнений и простотой механизма логического вывода.

От выбранной стратегии вывода зависит порядок применения и

срабатывания правил. Процедура выбора сводится к определению направления

поиска и способа его осуществления. В системе с прямым выводом по известным

фактам отыскивается заключение, которое из этих фактов следует. Если такое

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

часто называют выводом, управляемым данными, или выводом, управляемым

антецедентами.

База знаний в виде правил

1. Если горизонтальные полосы, то выравнивание печатной головки.

2. Если вертикальные полосы, то правильная установка чернил.

3. Если пропуск цветов, то правильная загрузка бумаги.

4. Если неправильные цвета, то чистка печатной головки.

5. Если размытый отпечаток, то установка необходимых драйверов.

6. Если неправильные символы, то установка необходимых драйверов.

7. Если неправильные поля, то правильность установки параметров страницы.

8. Если отпечатка чистых страниц, то установка необходимых драйверов.

9. Если отпечаток смазан, то правильная загрузка бумаги.

10.Если бумага не подается, то выравнивание печатной головки.

11.Если подача нескольких страниц за один раз, то правильная загрузка бумаги.

12.Если бумага заклинивается, то правильная загрузка бумаги.

33

Page 34: Учебное пособие по CLIPS

13. Если бумага мнется или не выводится полностью, то правильная загрузка

бумаги.

2.1.4. Реализация системы

Реализация — создание прототипа ЭС. На этом этапе создаётся прототип

ЭС, включающий базу знаний, на языке среды разработки CLIPS.

(defrule n1 ; Если горизонтальные полосы, то выравнивание печатной головки.

(horizontal strips)

=>

(printout t “leveling of the printed head” t))

(defrule n2 ; Если вертикальные полосы, то правильная установка чернил.

(vertical strips)

=>

(printout t “correct installation of ink” t))

(defrule n3 ; Если пропуск цветов, то правильная загрузка бумаги.

(passing of colours)

=>

(printout t “correct loading of a paper” t))

(defrule n4 ; Если неправильные цвета, то чистка печатной головки.

(incorrect colours)

=>

(printout t “cleaning of the printed head” t))

(defrule n5 ; Если размытый отпечаток, то установка необходимых драйверов.

(blurred impress)

=>

(printout t “installation of essential drivers” t))

(defrule n6 ; Если неправильные символы, то установка необходимых драйверов.

(incorrect characters)

=>

(printout t “installation of essential drivers” t))

(defrule n7

34

Page 35: Учебное пособие по CLIPS

; Если неправильные поля, то правильность установки параметров страницы.

(incorrect fields)

=>

(printout t “correctness of installation of parameters page” t))

(defrule n8

; Если отпечатка чистых страниц, то установка необходимых драйверов.

(impression of clean pages)

=>

(printout t “the installation of essential drivers” t))

(defrule n9 ; Если отпечаток смазан, то правильная загрузка бумаги.

(impression is lubricated)

=>

(printout t “correct loading of a paper” t))

(defrule n10 ; Если бумага не подается, то выравнивание печатной головки.

(paper does not move)

=>

(printout t “leveling of the printed head” t))

(defrule n11

; Если подача нескольких страниц за один раз, то правильная загрузка бумаги.

(submission of several pages for once)

=>

(printout t “correct loading of a paper” t))

(defrule n12 ; Если бумага заклинивается, то правильная загрузка бумаги.

(paper is jammed)

=>

(printout t “correct loading of a paper” t))

(defrule n13 ; Если бумага мнется или не выводится полностью,

; то правильная загрузка бумаги.

(paper is pressed or is not injected completely)

=>

35

Page 36: Учебное пособие по CLIPS

(printout t “correct loading of a paper” t))

В данной работе представленная БЗ при помощи встроенного редактора

CLIPS сохраняется, а затем загружается в систему.

2.1.5. Тестирование прототипа

Тестирование — выявление ошибок в реализации прототипа, оценка

разработанной БЗ.

Рекомендуется протестировать программу на 5 примерах. Для каждого

тестового примера

1) выполнить команду (reset);

2) добавить в список фактов из командной строки CLIPS какой-либо факт,

характеризующий ситуацию, например: (assert (paper is jammed));

3) сформировать файл отчёта при выполнении тестового примера.

2.2. Пример 2. Разработка ЭС диагностики неисправностей двигателя

Цель: разработать простейшую экспертную систему, которая позволяет по

имеющимся фактам определить неисправности в двигателе.

Постановка задачи: необходимо реализовать блок логического вывода

посредством CLIPS и протестировать его на наборе начальных фактов.

База знаний в виде правил

1. Если нет искры на свечах (there is no spark on suppositories), то двигатель не

запускается (engine is not started).

2. Если плохое соединение проводов (poor connection of wires), то малый ток в

первичной КЗ (small current in primary kz).

3. Если малый ток в первичной КЗ (small current in primary kz), то малый ток во

вторичной КЗ (small current in secondary kz).

4. Если малый ток во вторичной КЗ (small current in secondary kz), то слабая искра

на свечах (weak spark on suppositories).

5. Если слабая искра на свечах (weak spark on suppositories), то плохой

аккумулятор (bad accumulator).

36

Page 37: Учебное пособие по CLIPS

6. Если плохой аккумулятор (bad accumulator), то малый ток в первичной КЗ

(small current in primary kz).

7. Если слабо вращается коленвал (crankshaft is rotated weakly), то плохой

аккумулятор (bad accumulator).

8. Если пробит конденсатор (strike condenser), то нет тока в первичной КЗ (there is

no current in primary kz).

9. Если нет тока в первичной КЗ (there is no current in primary kz), то нет тока во

вторичной КЗ (there is no current in secondary kz).

10. Если нет тока во вторичной КЗ (there is no current in secondary kz), то нет

искры на свечах (there is no spark on suppositories).

Начальные факты

1. Слабая искра на свечах (weak spark on suppositories).

2. Слабо вращается коленвал (crankshaft is rotated weakly).

Для программной реализации необходимо:

1) сформировать БЗ при помощи встроенного редактора CLIPS и сохранить её

(для пояснения работы системы организовать вывод заключений правил на

экран);

2) выполнить команду (clear);

3) загрузить БЗ посредством команды (load);

4) задать набор начальных фактов конструкцией deffacts:

(deffacts sf (weak spark on suppositories) (crankshaft is rotated weakly))

5) выполнить команду (reset);

6) выполнить команду (run);

7) сформировать файл отчёта при выполнении примера.

2.3. Пример 3. Разработка ЭС организации отдыха

Цель: разработать простейшую экспертную систему, которая советует, где

лучше отдохнуть в отпуске.

37

Page 38: Учебное пособие по CLIPS

Постановка задачи: необходимо реализовать блок логического вывода

посредством CLIPS и протестировать его на различных наборах фактов. Создана

концептуальная структура, описывающая понятия данной предметной области.

Дополните самостоятельно данное поле знаний (его функциональную структуру).

Концептуализация знаний

Поле знаний состоит из концептуальной и функциональной структур

предметной области.

Концептуальная структура служит для описания объектов предметной

области и отношений между ними (см. табл.6 и табл. 7).

Таблица 6

Входные факторы

здоровье (health) материальное

положение (family

status)

время отпуска

(vacation time)

характер

(character)

1) плохое (bad) 1) ниже среднего

(below average)

1) зима (winter) 1) активный

(active)

2) среднее

(middle)

2) среднее

(average)

2) весна (spring) 2) пассивный

(passive)

3) нормальное

(normal)

3) хорошее (good) 3) лето (summer)

4) отличное

(excellent)

4) осень (autumn)

Таблица 7

Выходные факторы

активный отдых (active rest) пассивный отдых (passive rest)

1) поход (walking tour) 1)дача (dacha)

2) турпоездка (tourist trip) 2) курорт (resort)

3) деревня (village)

4) дом (home)

38

Page 39: Учебное пособие по CLIPS

Функциональная структура отражает модель рассуждения в процессе

принятия решений (см. табл.8).

Таблица 8

Функциональная структура

здоровье материальное

положение

время отпуска характер вид отдыха

отличное хорошее активный турпоездка

среднее лето пассивный Дача

ниже среднего осень пассивный Дом

- - - - - - - - - - - - - - -

Функциональная структура предметной области должна содержать не менее

10 строк.

Формализация

На основе функциональной структуры предметной области при помощи

встроенного редактора CLIPS создаётся БЗ, а затем сохраняется на диске и

загружается в систему.

Тестирование

Рекомендуется протестировать программу на 5 примерах. Для каждого

тестового примера

1) выполнить команду (reset);

2) добавить в список фактов из командной строки CLIPS какие-либо факты,

характеризующие ситуацию, например: (assert (excellent health) (active

character));

3) сформировать файл отчёта при выполнении тестового примера.

2.4. Задание

1. Реализовать примеры 1, 2 и 3, представленные в предыдущих пунктах

данного раздела. В отчёт о выполнении задания 2.4 поместить программы с

правилами и файлы отчёта по тестированию.

39

Page 40: Учебное пособие по CLIPS

2. Пример 4.

Цель: разработать простую и удобную в эксплуатации экспертную систему в

выбранной предметной области.

Постановка задачи: необходимо реализовать блок логического вывода

посредством CLIPS и протестировать его на различных наборах фактов.

В отчёт о выполнении задания 2.4 необходимо поместить концептуальную и

функциональную структуру предметной области, программу с правилами и

файлы отчёта по тестовым примерам.

3. ОБЪЕКТНО-ОРИЕНТИРОВАННОЕ ПРОГРАММИРОВАНИЕ В CLIPS

3.1. Объектно-ориентированные средства программирования

в системе CLIPS

Использование объектно-ориентированных средств в CLIPS позволяет

значительно упростить программирование правил, поскольку для обновления

данных можно применять механизм передачи и обработки сообщений методами

классов. Для этих целей разработана COOL ─ объектно-ориентированная

надстройка CLIPS (COOL – CLIPS object-oriented language).

В рамках единой CLIPS программы «уживаются» правила и объекты.

Правила управляют ходом вычислений, но некоторые операции объекты

выполняют и самостоятельно, получив «указание» (сообщение) от правил.

Объекты не являются резидентами рабочей памяти, но члены левой части правил

(условий) могут быть сопоставлены с содержимым их слотов. Состояние объектов

может измениться и вследствие побочных эффектов активизации правил, но луч-

ше предоставить объектам возможность самостоятельно выполнять манипуляции

с хранящимися в них данными в ответ на поступающие от правил сообщения.

Объекты не могут самостоятельно активизировать правила, но их обработчики

сообщения могут возвращать определенную информацию о результатах, которая

используется для управления логикой выполнения действий в правой части

правил.

40

Page 41: Учебное пособие по CLIPS

Идея объектно-ориентированного программирования состоит в том, что

программа строится вокруг множества объектов, каждый из которых обладает

собственным набором функций (операций). Вместо того чтобы представлять

объект пассивным набором данных, объектно-ориентированная система

позволяет объекту играть более активную роль, в частности взаимодействовать с

другими объектами, обмениваясь с ними сообщениями. В результате основной

упор переносится с разработки общей управляющей структуры программы,

которая ответственна за порядок обращения к функциям, на конструирование

самих объектов, выяснение их ролей и создание протоколов взаимодействия

объектов. Эти протоколы, по существу, определяют интерфейс между объектами.

Если один объект должен взаимодействовать с другим, он должен вызывать

функции в строгом соответствии с этим интерфейсом.

Объекты располагают собственными данными, которые играют ту же роль,

что и слоты фреймов, собственным механизмом обновления этих данных и

использования хранящейся в них информации. Помимо функций интерфейса,

объекты располагают собственными, «приватными» функциями, которые, как

правило, представляют собой реализацию определенной родовой операции

применительно к данному объекту. Помимо данных, передаваемых в качестве

аргументов родовой операции, такие функции используют и локальные данные

объекта — аналоги слотов фрейма.

Предположим, мы определили объект, представляющий класс ship (корабль),

и наделили его свойствами x-velocity (скорость по х) и y-velocity (скорость по у).

Теперь можно создать экземпляр класса ship, назвать его Titanic и одновременно

присвоить свойствам x-velocity и y-velocity нового экземпляра исходные значения.

Далее необходимо определить процедуру speed, которая будет вычислять

скорость судна на основании значений свойств x-velocity и y-velocity (скорость

вычисляется как квадратный корень из суммы квадратов компонентов). Такая

процедура будет принадлежать абстрактному типу данных, представляющему

любые суда (в терминологии языка SmallTalk speed — это метод класса ship, а в

терминологии С++ — функция-член класса ship.)

41

Page 42: Учебное пособие по CLIPS

Идея состоит в том, чтобы закодировать в объекте (классе) не только

декларативные знания о судах, но и процедурные, т.е. методы использования

декларативных знаний. Для того чтобы активизировать процедуру вычисления

скорости определенного судна, в частности «Титаника», нужно передать объекту

Titanic сообщение, которое побудит его обратиться к ассоциированной процедуре

в контексте данных о компонентах скорости именно этого объекта. Titanic — это

экземпляр класса ship, от которого он унаследовал процедуру speed.

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

следующие соглашения. Программа, разработанная в расчете на этот механизм,

должна следовать в дальнейшем определенному протоколу, определяющему

способ взаимодействия между объектами. Другими словами, интерфейс обмена

сообщениями между объектами должен быть досконально продуман, а правила

этого интерфейса жестко соблюдаться. Лучше всего продемонстрировать эту

мысль на примере.

Для того чтобы определить компоненту x текущего положения «Титаника»,

программа должна послать соответствующий запрос объекту Titanic. Как в

объекте формируется это значение или как оно хранится — дело только самого

объекта. Ни объекты других классов, ни какие-либо другие компоненты

программы этого не знают. Более того, внутренний механизм доступа к этой

информации должен быть скрыт, чтобы никто не имел доступ к ней, минуя сам

объект. Это соглашение принято называть инкапсуляцией.

Во-вторых, совершенно очевидна избыточность определения своего метода

вычисления скорости для каждого класса объектов, которые обладают

возможностью перемещаться в двумерной системе координат. Метод, который

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

других движущихся объектов, поскольку вычисление скорости представляет

собой родовую операцию. Поэтому имеет смысл связать этот метод с каким-

нибудь суперклассом транспортных средств, производными от которого будут

классы судов, автомобилей, троллейбусов и т.п. Все эти подклассы унаследуют

родовую операцию у своего базового класса.

42

Page 43: Учебное пособие по CLIPS

Такое наследование — это уже нечто большее, чем наследование свойств.

Выполнение родовых операций встраивается в механизм обмена сообщениями.

Отсылка сообщения — это отнюдь не вызов определенной процедуры, поскольку

вызывающий объект не знает, каким именно методом отреагирует на это сооб-

щение объект-получатель, от кого он унаследует этот метод, и будет ли вообще

задействован механизм наследования в данном конкретном случае.

Вызывающему объекту известны лишь наименование операции и ее внешние по

отношению к преемнику аргументы. Все остальное — заботы объекта-реципиента

сообщения.

Ниже показано, как на языке CLIPS определяется класс ship и формируется

экземпляр этого класса titanic. Сначала определим класс ship, в котором имеются

слоты x-velocity и y-velocity:

(defclass ship

(is-a USER)

(role concrete)

(pattern-match reactive)

(slot x-velocity (create-accessor read-write))

(slot y-velocity (create-accessor read-write)))

Первые три слота — системные. Они нужны объектно-ориентированной

надстройке COOL. Эти слоты извещают о том, что

• ship — это пользовательский класс;

• ship является конкретным классом, т.е. возможно создание экземпляров этого

класса (альтернативный тип — абстрактный класс, который играет туже роль, что

и виртуальный класс в С++);

• экземпляры класса ship могут быть использованы в качестве объектов данных,

которые можно сопоставлять с условиями в правилах и использовать в действиях,

определенных правилами.

Следующие слоты представляют свойства и члены данных класса.

Теперь сформируем экземпляр этого класса, которому будет дано

наименование «Titanic». Проще всего это сделать с помощью функции

43

Page 44: Учебное пособие по CLIPS

Многоугольник

Четырёхугольник

Трапеция

Параллелограмм

Прямоугольник

Квадрат

Рис. 1. Иерархия плоских геометрических фигур

definstances, которая в качестве аргументов принимает список параметров

формируемых экземпляров. Определённые таким образом экземпляры класса

будут инициализироваться при каждом перезапуске интерпретатора CLIPS.

(definstances ships

(titanic of ship (x-velocity 12) (y-velocity 10)))

Завершается определение созданием обработчика событий для класса ship.

Все экземпляры класса будут использовать этот обработчик для вычисления

собственной скорости. Обратите внимание на то, что в этом определении

ссылаются на значение слота того экземпляра класса, скорость которого

требуется вычислить.

(defmessage-handler ship speed ( )

(sqrt (+ (* ?self:x-velocity ?self:x-velocity)

(* ?self:y-velocity ?self:y-velocity))))

Если файл со всеми представленными выше

выражениями загрузить в среду CLIPS и

выполнить команду (reset), а затем ввести с

клавиатуры (send [titanic] speed), то в ответ

интерпретатор CLIPS выведет скорость объекта

titanic.

3.2. Реализация фреймов и наследования

в языке CLIPS

Хотя язык CLIPS и не поддерживает в явном

виде формализм семантических сетей и фреймов, их

можно неявно определить, используя имеющуюся

в CLIPS конструкцию defclass. Основное

назначение этой конструкции ― реализация

объектно-ориентированного подхода. Для

представления иерархии геометрических

объектов, показанной на рисунке 1, понадобятся

следующие определения:

44

Page 45: Учебное пособие по CLIPS

(defclass polygon (is-a USER))

(defclass quadrilateral (is-a polygon))

(defclass trapezium (is-a quadrilateral))

(defclass parallelogram (is-a trapezium))

(defclass rectangle (is-a parallelogram))

(defclass square (is-a rectangle))

Обратите внимание на то, что класс polygon (многоугольник) объявлен как

подкласс класса USER, который является базовым для всех классов, объявленных

пользователем. Отношение is-a (является), которое фигурирует во всех языках

представления фреймов, обычно обладает свойством транзитивности. Это

отношение является ассиметричным, т.е. если квадрат является

прямоугольником, то прямоугольник в общем случае не является квадратом.

Для того чтобы представить на языке CLIPS тот факт, что большинство

многоугольников должно иметь четыре стороны, потребуются дополнительные

языковые конструкции. Нужно несколько изменить определение классов polygon

и quadrilateral:

(defclass polygon (is-a USER)

(role abstract)

(slot no-of-sides (default 4)))

(defclass quadrilateral (is-a polygon)

(role concrete))

Теперь polygon объявлен как абстрактный класс, т.е. класс, не способный

самостоятельно порождать определённые объекты. Его подкласс quadrilateral и

все последующие подклассы класса quadrilateral являются конкретными

классами, т.е. эти классы могут порождать конкретные экземпляры (объекты

классов). При определении класса polygon его слоту no-of-sides (количество

сторон) назначено по умолчанию значение 4. Это отражает интуитивное

предположение, что большинство многоугольников будет четырёхугольниками.

В терминологии систем фреймов такое значение по умолчанию называется

фацетом слота no-of-sides.

45

Page 46: Учебное пособие по CLIPS

Слоты данных в языке COOL также поддерживают фацеты, т.е. свойства,

ответственные за доступ к слотам в процессе работы программы. Например,

существует фацет visibility (видимость), который определяет, какие другие классы

могут обратиться к слоту. Значение private означает, что только обработчик

сообщения данного класса может получить доступ к данным, а значение public

позволяет это сделать также обработчикам сообщений производных классов и

суперклассов.

После этого можно приступить к описанию обработчиков сообщений. Для

этого нужно воспользоваться конструкцией defmessage-handler, которая имеется в

CLIPS.

(defmessage-handler polygon sides ( )

?self:no-of-sides)

Обработчик сообщений sides связан с классом polygon и получает доступ к

слоту no-of-sides того объекта, который его вызвал. Подклассы могут наследовать

и слоты, и обработчики сообщений от своих суперклассов (предшественников).

Предположим, например, что определён конкретный участок, имеющий

форму квадрата, причём ему присвоено наименование square-one.

(definstances geometry

(square-one of square))

Система CLIPS инициализируется командой (reset). Далее можно

активизировать обработчик сообщений, послав ему сообщение

(send [square-one] sides)

В ответ интерпретатор CLIPS выведет результат

4

Обратите внимание на то, что выражение ?self:no-of-sides вычисляется в

контексте объекта square-one, которому было направлено сообщение и который в

ответ на него активизировал обработчик сообщений sides. В этом выражении ?

self является переменной и определяет объект, к слоту которого производится

обращение, а двоеточие ― это инфиксный оператор доступа к конкретному

слоту.

46

Page 47: Учебное пособие по CLIPS

3.3. Задание

1. Реализовать рассмотренный в пункте 3.1 пример в системе CLIPS.

Протестировать программу на 5 примерах с различными значениями компонент x

и y. По каждому примеру в отчёт о выполнении задания 3.3 поместить текст

программы и файлы отчёта с результатами работы программы.

2. Реализовать рассмотренный в пункте 3.2 пример. Получить указанный

результат. В отчёт о выполнении задания 3.3 поместить текст программы и файл

отчёта с результатом работы программы.

3. Для примера, реализованного в предыдущем пункте данного задания,

придумайте обработчик сообщения класса square, который будет вычислять

площадь объекта этого класса, например объекта square-one, а затем присваивать

вычисленное значение слоту этого объекта и выводить новое значение слота на

экран.

Для этого вам понадобится сначала внести изменения в определение класса

square:

(defclass square (is-a rectangle)

(slot length-of-sides)

(slot area))

Согласно этому определению, класс square имеет два слота: length-of-sides —

для хранения длин сторон объекта, area — для хранения его площади.

Второй шаг — модифицировать спецификацию объекта, в которую следует

включить задание длин сторон:

(definstances geometry

(square-one of square

(length-of-sides 10)))

Теперь остается только разработать обработчик события put-print-area класса

square, который будет использовать функцию bind для установки вычисляемого

значения площади в слот area и выводить новое значение этого слота на экран.

Система CLIPS инициализируется командой (reset). Далее можно

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

47

Page 48: Учебное пособие по CLIPS

(send [square-one] put-print-area).

В отчёт о выполнении задания 3.3 поместить текст программы и файл отчёта

с результатом работы программы.

4. В состав документации, которая прилагается к большинству приборов и

технических изделий, как правило, входят и руководства по поиску

неисправностей. Реализуйте в CLIPS представленную систему, основанную на

правилах, которая будет выполнять функции консультанта по поиску

неисправностей в револьвере.

;;*********************************************************************

;;* Поиск неисправностей в револьвере Smith & Wesson

;;*********************************************************************

;; Класс REVOLVER, определение компонентов

(defclass revolver

(is-a USER) (role concrete) (slot barrel) (slot barrel-pin) (slot cyl-stop) (slot cyl)

(slot handspring))

;; Экземпляр класса REVOLVER. Предназначен для тестирования программы.

(definstances guns

(M19 of revolver (barrel 4499) (barrel-pin 4499) (cyl-stop 4499) (cyl 4499)

(handspring 5022)))

;; МЕТОД. Получение номера детали револьвера

(defmessage-handler revolver part-no (?part)

(dynamic-get ?part))

;; ПОЛЕЗНЫЕ ФУНКЦИИ

;; Приглашение пользователю ввести данные

(deffunction prompt ( )

(printout t crlf “USER> “))

;; Распечатка списка деталей

;; Замечание: приведенный список правил касается только неисправностей со

стволом (barrel).

(deffunction parts-list ( )

48

Page 49: Учебное пособие по CLIPS

(printout t crlf “barrel cylinder ejector trigger hammer firing-pin cylinder-stop

cylinder-hand yoke frame sideplate rear-sight front-sight” crlf))

;; Выбор из списка.

(deffunction choose-list ()

(printout t crlf “Please choose from the following list: “ crlf))

;; Правила, которые относятся только к револьверам модели 19.

(deffunction kind-list ( )

(printout t crlf “M10 M12 M13 M14 M15 M16 M17 M18 M19 “ crlf))

;; ШАБЛОНЫ РЕШЕНИЯ ПРОБЛЕМЫ

;; Формулировка проблемы включает узлы (part), симптомы (symptom), возможно,

;; детали (subpart), входящие в состав узлов. С проблемой может быть связано

;; определенное испытание или проверка (check), которые нужно провести.

(deftemplate problem

(field part (type SYMBOL) (default nil)) (field symptom (type SYMBOL) (default

nil))

(field subpart (type SYMBOL) (default nil)) (field check (type SYMBOL) (default

nil)))

;; Определение процедуры ремонта включает: узел (part),

;; операцию c этим узлом (action), возможно, детали (subpart),

;; входящие в состав узлов, проверку (check), которую нужно провести,

;; и поясняющее примечание (remark), предназначенное для пользователя.

(deftemplate repair

(field part (type SYMBOL) (default nil)) (field action (type SYMBOL) (default

nil))

(field subpart (type SYMBOL) (default nil)) (field check (type SYMBOL) (default

nil))

(field remark (type STRING) (default “ “)))

;;*************************

;; Порождающие правила

;;*************************

49

Page 50: Учебное пособие по CLIPS

;; Правило START. ЕСЛИ: начинается выполнение программы ТО:

;; определить поврежденный узел и сформировать шаблон описания проблемы.

(defrule start

?start-token <- (initial-fact)

=>

(retract ?start-token)

(printout t crlf “What part of the gun are you problem with?” crlf)

;; С каким узлом у вас проблемы?

(choose-list) (parts-list) (prompt) (bind ?part (read))

(assert (problem (part ?part))))

;; Правило FINISH. ЕСЛИ: Неисправность устранена,

;; TO: Прекратить работу программы.

(defrule finish

(repair (check done) (remark ?rem&~” “))

=>

(printout t crlf ?rem crlf)

(printout t crlf “Glad to be of service!” crlf)

;; Рад быть вам полезным!

(halt)) ;; Остановка выполнения правил.

;; Правило CHECK-REPAIR. ЕСЛИ: Имеется решение менее радикальное,

;; чем замена, ТО: Информировать пользователя и отметить,

;; что неисправность (проблема) может быть устранена путем ремонта.

(defrule check-repair

?rep <- (repair (part ?part) (action ?action&~replace)

(subpart ?sub&~nil&~?part))

(problem (part ?part) (symptom ?sym))

=>

(printout t crlf “If you “ ?action “ the “ ?sub “ that should fix the “ ?sym

“ problem with the “ ?part crlf)

;; “Если вы “ ?action ?sub “ то -это должно устранить “ ?sym “ проблемы с “ ?part

50

Page 51: Учебное пособие по CLIPS

(modify ?rep (check done)))

;; Правило CHECK-REPLACE. ЕСЛИ: Решение требует замены узла

;; ТО: Информировать пользователя и отметить,

;; что неисправность (проблема) устранена.

;; Для этого добавить в рабочую память пустой вектор

;; и запросить у пользователя наименование модели изделия.

(defrule check-replace

(repair (part ?part) (action replace)) (not (model ?mod&~nil))

?prob <- (problem (part ?part) (symptom ?sym))

=>

(printout t crlf “You have to replace the “ ?part “ to fix the “ ?sym “ problem “ crlf)

;; “Вам потребуется заменить “ ?part “чтобы устранить “ ?sym “ проблемы “

(assert (model nil)))

;; Правило REPLACE. ЕСЛИ: Пользователю необходимо заменить узел

;; ТО: Запросить у пользователя наименование модели изделия.

(defrule replace

?rep <- (repair (action replace)) ?mod <- (model nil)

=>

(printout t crlf “What model of revolver do you have ?” crlf)

;; “Какой модели ваш револьвер?”

(kind-list) (prompt) (bind ?answer (read)) (retract ?mod) (assert (model ?answer))

(modify ?rep (check part-no)))

;; Правило PART-NO. ЕСЛИ: Пользователю необходимо заменить узел

;; ТО: Выяснить номер узла, отослав сообщение объекту, представляющему

данную модель изделия.

(defrule part-no

(model ?mod&~nil)

?rep <- (repair (part ?part) (action replace) (check part-no))

=>

(bind ?no (send (symbol-to-instance-name ?mod) part-no ?part))

51

Page 52: Учебное пособие по CLIPS

(printout t crlf “The part number of the “ ?mod “ “ ?part “ is “ ?no crlf)

;; “Номер узла “ ?mod “ “ ?part ?no

(modify ?rep (check done)))

;; Правила BARREL (ствол)

;; Правило BARREL-SYMPTOM. ЕСЛИ: Неисправность не имеет признаков

;; ТО: Выяснить признак (симптом).

(defrule barrel-symptom

?prob <- (problem (part barrel) (symptom nil) (subpart nil))

=>

(printout t crlf “Is there a problem inside barrel? “ crlf)

;; “Есть ли повреждения внутри ствола?”

(prompt) (bind ?answer (read))

(if (eq ?answer yes) then (modify ?prob (subpart bore))))

;; Правило BARREL-INSIDE. ЕСЛИ: Имеется повреждение канала ствола

;; ТО: Выяснить у пользователя, какое (и предложить помощь).

(defrule barrel-inside

?prob <- (problem (part barrel) (symptom nil) (subpart bore))

=>

(printout t crlf “What is the problem inside the barrel? “ crlf)

;; “Характер повреждения канала ствола?”

(choose-list) (printout t crlf “ leading rust jam” crlf)

;; “ наличие ржавчины”

(prompt) (bind ?answer (read)) (modify ?prob (symptom ?answer)))

;; Правило BARREL-RUST. ЕСЛИ: Имеется ржавчина в канале ствола

;; ТО: Проверить наличие раковин.

(defrule barrel-rust

?prob <- (problem (part barrel) (symptom rust))

=>

(printout t crlf “Are there pits inside the barrel? “ crlf)

;; “Нет ли раковин в канале ствола?”

52

Page 53: Учебное пособие по CLIPS

(prompt) (bind ?answer (read))

(if (eq ?answer yes) then (assert (repair (action replace) (part barrel) (subpart bore)

(remark “Please consult your local dealer”)))

;; Проконсультируйтесь с местным дилером

else (assert (repair (action clean) (part barrel) (subpart bore)

(remark “Gun should be kept clean and dry”)))

;; Оружие нужно содержать в чистоте и предохранять от сырости

))

;; Правило BARREL-LEADING. ЕСЛИ: Имеется налет свинца в канале ствола

;; ТО: Проверить качество патронов.

(defrule barrel-leading

?prob <- (problem (part barrel) (symptom leading) (check nil))

=>

(modify ?prob (check ammo))

(printout t crlf “You may be using the wrong ammunition “ crlf))

;; “Возможно, вы пользуетесь некачественными патронами”

;; Правило BARREL-LEADING-CHECK.

;; ЕСЛИ: Имеется налет свинца в канале ствола,

;; ТО: Проверить качество патронов.

(defrule barrel-leading-check

?prob <- (problem (part barrel) (symptom leading) (check ammo))

=>

(assert (repair (part barrel) (action clean) (subpart bore)

(remark “Use Lewis Lead Remover”))))

;; Воспользуйтесь средством для удаления свинца фирмы Lewis

Система CLIPS инициализируется командой (reset). Запуск программы на

выполнение осуществляется командой (run).

Необходимо протестировать программу на 5 примерах для получения

рекомендаций, связанных со стволом (barrel) револьвера (M19). Проблемы

53

Page 54: Учебное пособие по CLIPS

имеются внутри ствола (inside), и они касаются наличия ржавчины (rust) и налёта

свинца (leading). В отчёт о выполнении задания 3.3 поместить текст программы и

файлы отчёта с результатами работы программы.

5. Для выбранной предметной области на основе программы предыдущего

пункта данного задания разработайте объектно-ориентированную программу и

протестируйте её на достаточном количестве примеров. В отчёт о выполнении

задания 3.3 поместить текст программы и файлы отчёта с результатaми работы

программы.

4. РЕШЕНИЕ ЛОГИЧЕСКИХ ЗАДАЧ В CLIPS

4.1. Задача «Правдолюбцы и лжецы»

Для того чтобы продемонстрировать возможности языка CLIPS, выбрана

головоломка. В головоломке решается одна из задач, возникающих на острове,

населенном обитателями двух категорий: одни всегда говорят правду (назовем их

правдолюбцами), а другие всегда лгут (их, естественно, назовем лжецами). Ниже

приведены разные задачи из этой серии.

Р1. Встречаются два человека, А и В, один из который правдолюбец, а

другой — лжец. А говорит. «Либо я лжец, либо В правдолюбец». Кто из этих

двоих правдолюбец, а кто лжец?

Р2. Встречаются три человека. А, В и С. А и говорит: «Все мы лжецы», a В

отвечает: «Только один из нас правдолюбец». Кто из этих троих правдолюбец, а

кто лжец?»

4.2. Анализ проблемы

Первым этапом любого программного проекта является анализ решаемой

проблемы. Эксперт должен уметь решить проблему, а инженер по знаниям

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

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

случится, если персонаж, произносящий реплику, является правдолюбцем, а что,

если он — лжец. Обозначим через Т(А) факт, что А говорит правду и,

54

Page 55: Учебное пособие по CLIPS

следовательно, является правдолюбцем, а через F(A) — факт, что А лжет и,

следовательно, является лжецом.

Рассмотрим сначала головоломку Р1. Предположим, что А говорит правду.

Тогда из его реплики следует, что либо А лжец, либо В правдолюбец. Формально

это можно представить в следующем виде:

T(A) => F(A) v T(B).

Поскольку А не может быть одновременно и лжецом и правдолюбцем, то

отсюда следует

T(A) => T(B).

Аналогично можно записать и другой вариант. Предположим, что А лжет:

F(A) => ~(F(A) v T(B)).

Упростим это выражение:

F(A) => ~F(A) ^ ~T(B) или F(A) => T(A) ^ F(B).

Сравнивая оба варианта, нетрудно прийти к выводу, что только последний

правильный, поскольку в первом варианте мы пришли к выводу,

противоречащему условиям (не могут быть правдолюбцами одновременно А и В).

Таким образом, рассматриваемая проблема относится к типу таких, решение

которых находится в результате анализа выводов, следующих из определенных

предположений, и поиска в них противоречий (или отсутствия таковых). Мы

предполагаем, что определённый персонаж говорит правду, а затем смотрим,

можно ли в этом случае так распределить «роли» остальных персонажей, что не

будут нарушены условия, сформулированные в репликах. В математической

логике, предположение о правдивости или лживости множества высказываний

называется интерпретацией, а вариант непротиворечивого присвоения значений

истинности элементам множества — моделью.

На практике оказывается, что в первой версии программы удобнее всего

воспользоваться «вырожденным» вариантом проблемы, т.е. постараться решить

ее в тривиальном виде, который, тем не менее, несет в себе многие особенности

реального случая. Вот как это выглядит в отношении правдолюбцев и лжецов.

55

Page 56: Учебное пособие по CLIPS

Р0. А заявляет: «Я лжец». Кто же в действительности А — лжец или

правдолюбец?

Мы только что фактически процитировали хорошо известный Парадокс

Лгуна. Если А лжец, то, значит, он врет, т.е. в действительности он правдолюбец.

Но тогда мы приходим к противоречию. Если же А правдолюбец, т.е. говорит

правду, то в действительности он лжец, а это опять противоречие. Таким образом,

в этой головоломке не существует непротиворечивого варианта «распределения

ролей», т.е. не существует модели в том смысле, который придается ей в

математической логике.

В то же время существенные черты проблемы в этом варианте присутствуют.

Мы по-прежнему должны попытаться отыскать непротиворечивую

интерпретацию высказывания А, т.е. должны реализовать две задачи,

присутствующие в любых вариантах подобной головоломки:

• формировать альтернативные интерпретации высказываниям;

• анализировать наличие противоречий.

4.3. Онтологический анализ и представление знаний

Следующий этап — определить, с какими видами данных придется иметь

дело при решении этого класса головоломок. Какие объекты представляют

интерес в мире правдолюбцев и лжецов и какими атрибутами эти объекты

характеризуются?

По-видимому, для решения задач этого класса нам придется иметь дело со

следующими объектами:

Персонажи, произносящие реплики. Произносимая реплика характеризует

либо самого персонажа, либо прочих персонажей, либо и тех и других.

Персонаж может быть либо правдолюбцем, либо лжецом.

Утверждение, содержащееся в реплике. Это утверждение может быть либо

целиком лживым, либо абсолютно правдивым (истинным).

Существуют еще и другие объекты, которые необходимо учитывать при

решении задач этого класса.

56

Page 57: Учебное пособие по CLIPS

Существует среда (мир), которая характеризуется совокупностью наших

предположений. Например, существует мир,в котором мы предположили, что А

— правдолюбец, а следовательно, высказанное им утверждение (или

утверждения) истинно. Это предположение влечет за собой разные следствия,

которые образуют контекст данного гипотетического мира.

Существует еще нечто, что мы назовем причинами, или причинными

связями (reasons), которые связывают высказывания в том или ином

гипотетическом мире. Если А утверждает, что «В — лжец», и мы предполагаем,

что А — правдолюбец, то это утверждение является причиной (основанием), по

которой мы можем утверждать, что в данном гипотетическом мире В — лжец, а

следовательно, все утверждения, которые содержатся в репликах,

произносимых В, лживы. Отслеживая такие связи между высказываниями,

можно восстановить исходное состояние проблемы, если в результате

рассуждений мы придем к противоречию.

Естественно, что эти объекты можно представлять в программе по-разному.

Онтологический анализ практически никогда не приводит к единственному

способу представления. Для первой версии CLIPS-программы выбрано

следующее представление описанных объектов:

;; Объект statement (высказывание) связан с определенным

;; персонажем (поле speaker).

;; Высказывание содержит утверждение (поле claim).

;; Высказывание имеет основание - причину (поле reason),

;; по которой ему можно доверять,

;; и тэг (tag) - это может быть произвольный идентификатор.

(deftemplate statement

(field speaker (type SYMBOL))

(multifield claim (type SYMBOL))

(multifield reason (type INTEGER) (default 0))

(field tag (type INTEGER) (default 1)))57

Page 58: Учебное пособие по CLIPS

Вместо того чтобы фокусировать внимание на персонаже, во главу угла

ставится произносимая им реплика (высказывание), а персонаж относится к

атрибутам высказывания. Таким образом обеспечивается возможность

представить определённую головоломку в виде экземпляра шаблона,

приведенного ниже.

(statement (speaker A) (claim F A))

Этот шаблон можно интерпретировать следующим образом: «Существует

высказывание, сделанное персонажем А, в котором утверждается, что А лжец и

тэг этого высказывания по умолчанию получает значение 1». Обратите внимание

на то, что в поле reason также будет установлено значение по умолчанию (это

значение равно 0), т.е. можно предположить, что никаких предшествующих

высказываний, которые могли бы подтвердить данное, в этой задаче не было.

Поля claim и reason имеют квалификатор multifield, поскольку они могут

содержать несколько элементов данных.

Однако недостаточно только представить в программе высказывания

персонажей — нам понадобится также выявить суть содержащихся в них

утверждений. Далее, приняв определенное предположение о правдивости или

лживости персонажа, которому принадлежит высказывание, можно построить

гипотезу об истинности или лживости этого утверждения. С каждым таким

утверждением свяжем уникальный числовой идентификатор.

;; Утверждение, смысл которого, например, состоит в следующем,

;; Т А ... означает, что А правдолюбец;

;; F А ... означает, что А лжец.

;; Утверждение может иметь под собой основание (reason)

;; - обычно это тэг высказывания (объекта statement)

;; или тэг другого утверждения (объекта claim).

;; Утверждение также характеризуется признаком scope,

;; который может принимать значение «истина» или «ложь».

(deftemplate claim

(multifield content (type SYMBOL)) 58

Page 59: Учебное пособие по CLIPS

(multifield reason (type INTEGER) (default 0))

(field scope (type SYMBOL)))

Например, раскрыв содержимое приведенного выше высказывания в

предположении, что А говорит правду, получим следующее утверждение (объект

claim):

(claim (content F A) (reason 1) (scope truth)).

Таким образом, объект claim наследует содержимое от объекта statement.

Последний становится обоснованием (reason) данного утверждения. Поле scope

объекта claim принимает значение предположения о правдивости или лживости

этого высказывания.

Еще потребуется представление в программе того мира (world), в котором

мы в настоящее время находимся. Объекты world порождаются в момент, когда

мы формируем определенные предположения. Нужно иметь возможность

различать разные множества предположений и идентифицировать их в программе

в тот момент, когда процесс размышлений приводит нас к противоречию.

Например, противоречие между высказываниями Т(А) и F(A) отсутствует, если

они истинны в разных мирах, т.е. при разных предположениях.

Миры будем представлять в программе следующим образом:

;; Объект world представляет контекст,

;; сформированный определенными предположениями

;; о правдивости или лживости персонажей.

;; Объект имеет уникальный идентификатор в поле tag,

;; а смысл допущения – истинность или лживость – фиксируется в поле scope.

(deftemplate world

(field tag (type INTEGER) (default 1))

(field scope (type SYMBOL) (default truth)))

Обратите внимание на то, что при указанных в шаблоне значениях по

умолчанию мы можем начинать каждый процесс вычислений с объекта world,

имеющего в поле tag значение 1, причем этот «мир» можно заселить

высказываниями персонажей, которых мы предположительно считаем 59

Page 60: Учебное пособие по CLIPS

правдолюбцами. Таким образом можно инициализировать базу фактов the-facts

для задачи Р0 следующим образом:

;; Утверждение, что А лжец.

(deffacts the-facts (world) (statement (speaker A) (claim F A)))

Если этот оператор deffacts будет включен в тот же файл, что и объявления

шаблонов (а также правила, о которых речь пойдет ниже), то после загрузки этого

файла в среду CLIPS нам понадобится для запуска программы дать только

команду reset.

4.4. Разработка правил

В этом разделе мы рассмотрим набор правил, который помогает справиться с

вырожденной формулировкой Р0 задачи о лжецах и правдолюбцах. Первые два

правила, unwrap-true и unwrap-false, извлекают содержимое высказывания в

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

соответственно правдолюбцем или лжецом, и на этом основании формируют

объект claim.

;; Извлечение содержимого высказывания.

(defrule unwrap-true

(world (tag ?N) (scope truth))

(statement (speaker ?X) (claim $?Y) (tag ?N))

=>

(assert (claim (content T ?X) (reason ?N) (scope truth)))

(assert (claim (content $?Y) (reason ?N) (scope truth))))

(defrule unwrap-false

(world (tag ?N) (scope falsity))

(statement (speaker ?X) (claim $?Y) (tag ?N))

=>

(assert (claim (content F ?X) (reason ?N) (scope falsity)))

(assert (claim (content NOT $?Y) (reason ?N) (scope falsity))))

60

Page 61: Учебное пособие по CLIPS

В каждом из приведенных правил оператор в условной части делает предпо-

ложение соответственно о правдивости или лживости персонажа, а оператор в за-

ключительной части правила распространяет предположение на формируемые

утверждения — объекты claim.

Далее понадобятся правила, которые введут отрицания в выражения.

Поскольку ~Т(А) эквивалентно F(A), a — ~F(A) эквивалентно Т(А), то правила,

выполняющие соответствующие преобразования, написать довольно просто.

Анализ результатов применения этих правил значительно упростит выявление

противоречий, следующих из определенного предположения.

;; Правила отрицания

(defrule not1

?F <- (claim (content NOT T ?P))

=>

(modify ?F (content F ?P)))

(defrule not2

?F <- (claim (content NOT F ?P))

=>

(modify ?F (content T ?P)))

;; Выявление противоречия между предположением о

;; правдивости и следующими из него фактами.

(defrule contra-truth

(declare (salience 10))

?W <- (world (tag ?N) (scope truth))

?S <- (statement (speaker ?Y) ( tag ?N))

?P <- (claim (content T ?X) (reason ?N) (scope truth))

?Q <- (claim (content F ?X) (reason ?N) (scope truth))

=>

(printout t crlf “Statement is inconsistent if “ ?Y “ is a knight.”

;; “Высказывание противоречиво, если “ ?Y “ правдолюбец. “

t crlf)61

Page 62: Учебное пособие по CLIPS

(retract ?Q) (retract ?P)

(modify ?W (scope falsity)))

Если предположить, что исходное высказывание было правдивым, то в

дальнейшем обнаруживается противоречивая пара утверждений, которые затем

удаляются из рабочей памяти, а значение «правдивости» предположений в

объекте world изменяется на falsity (лживость). Если же после этого также будет

обнаружено противоречие, то мы приходим к выводу о глобальной

несовместимости условий задачи, т.е. в данной постановке мы имеем дело с

логическим парадоксом.

;; Выявление противоречия между предположением о

;; лживости и следующими из него фактами.

(defrule contra-falsity

(declare (salience 10))

?W <- (world (tag ?N) (scope falsity))

?S <- (statement (speaker ?Y) (tag ?N))

?P <- (claim (content F ?X) (reason ?N) (scope falsity))

?Q <- (claim (content T ?X) (reason ?N) (scope falsity))

=>

(printout t crlf “Statement is inconsistent if “ ?Y “ is a knave. “

;; “Высказывание противоречиво, если “ ?Y “ лжец.”

t crlf)

(modify ?W (scope contra)))

Правило sweep обеспечивает проверку, все ли следствия из неверного

предположения удалены из памяти.

;; Удалить из базы фактов все утверждения,

;; которые следуют из предположения о правдивости.

(defrule sweep

(declare (salience 20))

(world (tag ?N) (scope falsity))

?F <- (claim (reason ?N) (scope truth))

62

Page 63: Учебное пособие по CLIPS

=>

(retract ?F))

Обратите внимание на то, что правила contra-truth, contra-falsity и sweep

имеют более высокий приоритет (значение параметра salience), чем другие

правила. Этим обеспечивается как можно более ранее обнаружение противоречия,

а следовательно, и удаление из базы фактов утверждений, сделанных на основе

предположения, приведшего к противоречию.

Если теперь запустить на выполнение программу, представив ей исходный

набор фактов, соответствующих условию задачи Р0, то программа обнаружит, что

оба контекста противоречивы. Другими словами, независимо от того,

предполагаем ли мы, что А говорит правду или лжет, программа обнаружит

противоречие в контексте world.

4.5. Расширение набора правил — работа с составными высказываниями

Расширим теперь возможности программы таким образом, чтобы она могла

работать с составными высказываниями. Это даст возможность охватить в ней не

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

сложные. За основу возьмем следующую головоломку.

Р3. Встречаются два персонажа, А и В, каждый из которых либо лжец, либо

правдолюбец. Персонаж А говорит: «Мы оба лжецы». К какой категории следует

отнести каждого из них?

В этой задаче нам придется иметь дело с конъюнкцией, поскольку

утверждение, высказанное персонажем А, моделируется выражением

F(A) ^ F(B).

Эту конъюнкцию нужно разделить на выражения-компоненты и

проанализировать их непротиворечивость. Очевидно, что А не может быть

правдолюбцем, поскольку это противоречит утверждению, которое содержится в

его реплике. Но программа должна самостоятельно «распаковать» эту

конъюнкция для того, чтобы прийти к такому выводу.

63

Page 64: Учебное пособие по CLIPS

Нам также понадобится снабдить программу и средствами обработки

дизъюнкции, поскольку, если предположить, что А лжет, нужно будет

оперировать с отрицанием этого утверждения, которое преобразует выражение

F(A) ^ F(B)

в

T(A) v T(B).

Таким образом, в программу нужно включить правило выполнения

отрицания составных высказываний и правило, которое «понимало бы», что

дизъюнкты вроде T(А) в действительности являются предположениями.

Составное выражение T(A) v T(B) будем обрабатывать, предположив Т(А) и

проанализируем, нет ли в нем противоречия. Если таковое не обнаружится, то

можно предположить, что T(A) v T(B) совместимо с утверждением о том, что А

лгун, т.е. F(A). Но если предположение Т(А) приведет к несовместимости, то

нужно отказаться от него и предположить T(B). Если и это предположение

приведет к несовместимости, то это означает, что утверждение T(A) v T(B)

несовместимо с предположением F(A). В противном случае T(В) образует часть

совместимой интерпретации исходного высказывания.

В CLIPS составные высказывания проще всего представлять с помощью

префиксной нотации операций. Суть этого способа представления операций

состоит в том, что символ операции предшествует символам операндов. Каждый

оператор имеет фиксированное количество операндов, а потому всегда сущест-

вует возможность однозначно установить область действия операции даже в

случае, если операнды представляют собой вложенные выражения. Таким

образом, выражение, представленное скобочной формой ~(F(A) ^ T(В)), в

префиксной записи будет иметь вид

NOT AND F A T B.

Легче всего восстановить исходный вид выражения, представленного в

префиксной нотации, просматривая его справа налево. При этом операнды

считываются до тех пор, пока не встретится объединяющий их оператор.

Полученное выражение оказывается операндом следующего оператора. В 64

Page 65: Учебное пособие по CLIPS

представленном выше выражении B является операндом одноместного оператора

Т, а пара операндов T(В) и F(A) объединяется оператором AND.

Задавшись таким способом представления составных высказываний,

сформируем правило выполнения отрицания дизъюнктивной и конъюнктивной

форм, в котором будет использоваться функция flip, заменяющая «Т» на «F» и

наоборот.

(defrule not-or

?F <- (claim (content NOT OR ?P ?X ?Q ?Y))

=>

(modify ?F (content AND (flip ?P) ?X (flip ?Q) ?Y)))

(defrule not-and

?F <- (claim (content NOT AND ?P ?X ?Q ?Y))

=>

(modify ?F (content OR (flip ?P) ?X (flip ?Q) ?Y)))

Использование функции flip упрощает преобразование и позволит перейти от

выражения

NOT AND F A T B

прямо к

OR T A F B,

минуя

OR NOT F A NOT Т В.

Функция flip определена следующим образом:

(deffunction flip (?P)

(if (eq ?P T) then F else T))

Для упрощения ограничимся утверждениями в виде простых дизъюнкций

или конъюнкций вида

T(A) v T(B)

или

F(A) ^ T(B),

но не будем использовать более сложные утверждения в форме

65

Page 66: Учебное пособие по CLIPS

F(B) ^ (T(A) v T(B))

или

~(F(A) v F(B)) ^ (T(A) v T(B)),

поскольку для решения большинства интересных головоломок вполне достаточно

простых выражений.

Наибольшие сложности при модификации нашей программы связаны с

обработкой дизъюнктивных выражений, поскольку вывод о наличии

противоречия может 6ыть сделан только после завершения анализа всех членов

операндов дизъюнкции. Например, нет противоречия между F(A) и T(A) v F(B).

Противоречие, которое обнаружится при обработке первого операнда

дизъюнкции T(A) в предположении F(A), будет локальным в контексте T(A). Но

если мы вернемся к исходной дизъюнкции и попробуем проанализировать

контекст F(B), то никакого противоречия обнаружено не будет, и, следовательно,

интерпретация найдена.

Реализовать такой анализ локальных и глобальных противоречий можно,

добавив в шаблон объекта claim атрибут context:

(deftemplate claim

(multifield content (type SYMBOL))

(multifield reason (type INTEGER) (default 0))

(field scope (type SYMBOL))

(field context (type INTEGER) (default 0)))

Значение 0 в поле context означает, что мы имеем дело с глобальным

контекстом, значение 1 - с локальным контекстом левого операнда, а значение 2 –

с локальным контекстом правого операнда дизъюнкции. Пусть, например,

анализируется дизъюнкция

T(A) v F(B),

причем T(A) будет истинным в контексте 1, a F(B) — истинным в контексте 2. В

этом случае все выражение будет истинным глобально, т.е. в контексте 0.

66

Page 67: Учебное пособие по CLIPS

Структуру объекта world также нужно модифицировать — внести в нее поле

context. Это позволит отслеживать ход вычислений. Пусть, например, объект

world имеет вид

(world (tag 1) (scope truth) (context 2)).

Это означает, что данный «мир» создан следующей парой предположений:

• истинно высказывание, имеющее идентификатор (tag), равный 1, и

• правый операнд утверждения, которое содержится в этом высказывании,

имеет значение «истина».

Новый вариант шаблона объекта world приведен ниже.

;; Объект world представляет контекст,

;; сформированный определенными предположениями

;; о правдивости или лживости персонажей.

;; Объект имеет уникальный идентификатор в поле tag,

;; а смысл допущения - истинность или лживость

;; фиксируется в поле scope.

;; В поле context сохраняется текущий контекст

;; анализируемого операнда дизъюнкции.

;; 0 означает глобальный контекст дизъюнкции,

;; 1 означает левый операнд, 2 означает правый операнд.

(deftemplate world

(field tag (type INTEGER) (default 1))

(field scope (type SYMBOL) (default truth))

(field context (type INTEGER) (default 0)))

Следующий шаг ― разработка правил, манипулирующих контекстом.

Приведённое ниже правило формирует контекст для левого операнда дизюнкции.

(defrule left-or

?W <- (world (tag ?N) (context 0))

(claim (content OR ?P ?X ?Q ?Y) (reason ?N) (scope ?V))

=>

67

Page 68: Учебное пособие по CLIPS

(modify ?W (context 1))

(assert (claim (content ?P ?X) (reason ?N) (scope ?V) (context 1))))

Это правило устанавливает значение 1 в поле context объекта world и

формирует соответствующий объект claim.

По этому же принципу разработаем правило для формирования контекста

правого операнда дизъюнкции.

(defrule right-or

?W <- (world (tag ?N) (context 1))

(claim (content OR ?P ?X ?Q ?Y) (reason ?N) (scope ?V))

=>

(modify ?W (context 2))

(assert (claim (content ?Q ?Y) (reason ?N) (scope ?V) (context 2))))

Далее разработаем правила, чувствительные к контексту, которые будут

выявлять наличие противоречий в анализируемых утверждениях.

;; Выявление противоречия между предположением о

;; правдивости и следующими из него фактами

;; в разных контекстах одного и того же объекта world.

(defrule contra-truth-scope

(declare (salience 10))

(world (tag ?N) (scope truth) (context ?T))

(claim (content T ?X) (reason ?N) (scope truth) (context ?S&:(< ?S ?T)))

?Q <- (claim (content F ?X) (reason ?N) (scope truth) (context ?T))

=>

(printout t “Disjunct “ ?T “ is inconsistent with earlier truth context. “

;; “Дизъюнкт “ ?T

;; “ противоречит ранее установленному контексту правдивости.”

crlf)

(retract ?Q))

;; Выявление противоречия между предположением о

;; лживости и следующими из него фактами 68

Page 69: Учебное пособие по CLIPS

;; в разных контекстах одного и того же объекта world.

(defrule contra-falsity-scope

(declare (salience 10))

?W <- (world (tag ?N) (scope falsity) (context ?T))

(claim (content F ?X) (reason ?N) (scope falsity) (context ?S&:(< ?S ?T)))

?Q <- (claim (content T ?X) (reason ?N) (scope falsity) (context ?T))

=>

(printout t “Disjunct “ ?T “ is inconsistent with earlier falsity context.”

;; “Дизъюнкт “ ?T

;; “ противоречит ранее установленному контексту лживости.”

crlf)

(retract ?Q))

Нам потребуется модифицировать и прежние варианты правил contra-truth и

contra-falsity.

;; Выявление противоречия между предположением о

;; правдивости и следующими из него фактами

;; в одном и том же контексте одного и того же объекта world.

(defrule contra-truth

(declare (salience 10))

?W <- (world (tag ?N) (scope truth))

?P <- (claim (content T ?X) (reason ?N) (context ?S) (scope truth))

?Q <- (claim (content F ?X) (reason ?N) (context ?S) (scope truth))

=>

(printout t “Statement is inconsistent if “ ?X “ is a knight”

;; “Высказывание противоречиво, если “ ?X “ правдолюбец.”

crlf)

(retract ?Q) (retract ?P)

(modify ?W (scope falsity) (context 0)))

;; Выявление противоречия между предположением о

;; лживости и следующими из него фактами

69

Page 70: Учебное пособие по CLIPS

;; в одном и том же контексте одного и того же объекта world.

(defrule contra-falsity

(declare (salience 10))

?W <- (world (tag ?N) (scope falsity))

?P <- (claim (content F ?X) (reason ?N) (context ?S) (scope falsity))

?Q <- (claim (content T ?X) (reason ?N) (context ?S) (scope falsity))

=>

(printout t “Statement is inconsistent whether “ ?X “ is knight or knave.”

;; “Высказывание противоречиво, независимо от того, “

;; “является ли “ ?X “ правдолюбцем или лжецом. “

crlf)

(modify ?W (scope contra)))

Поскольку теперь постановка задачи усложнилась по сравнению с

вырожденным случаем, имеет смысл включить в программу распечатку

предположений о характеристиках персонажей, упомянутых в высказываниях.

(defrule consist-truth

(declare (salience -10))

?W <- (world (tag ?N) (scope truth))

(statement (speaker ?Y) (tag ?N))

=>

(printout t “Statement is consistent:”

;; “Высказывание непротиворечиво:”

crlf)

(modify ?W (scope consist)))

(defrule consist-falsity

(declare (salience -10))

?W <- (world (tag ?N) (scope falsity))

(statement (speaker ?Y) (tag ?N))

=>

(printout t “Statement is consistent: “

70

Page 71: Учебное пособие по CLIPS

;; “Высказывание непротиворечиво:”

crlf)

(modify ?W (scope consist)))

(defrule true-knight

(world (tag ?N) (scope consist))

?C <- (claim (content T ?X) (reason ?N))

=>

(printout t ?X “ is a knight”

;; ?X “ – правдолюбец”

crlf)

(retract ?C))

(defrule false-knave

(world (tag ?M) (scope consist))

?C <- (claim (content F ?X) (reason ?N))

=>

(printout t ?X “ is a knave”

;; ?X “ лжец”

crlf)

(retract ?C))

Ниже приведено правило разделения операции конъюнкции. Обратите

внимание на то, что в нем также отслеживается контекст, хотя в данном случае

без этого можно было бы и обойтись.

(defrule conj

(world (tag ?N) (context ?S))

(claim (content AND ?P ?X ?Q ?Y) (reason ?N) (scope ?V))

=>

(assert (claim (content ?P ?X) (reason ?N) (scope ?V) (context ?S)))

(assert (claim (content ?Q ?Y) (reason ?N) (scope ?V) (context ?S))))

Прежде чем запустить программу на выполнение, сформируем исходные

факты в соответствии с условиями задачи Р3:

71

Page 72: Учебное пособие по CLIPS

(deffacts the-facts

(world)

(statement (speaker A) (claim AND F A F B) (tag 1)))

4.6. Задание

1. Реализовать в системе CLIPS задачу P0.

2. Реализовать в системе CLIPS задачу P3.

ЛИТЕРАТУРА

1. Гаврилова Т.А., Хорошевский В.Ф. Базы знаний интеллектуальных систем. –

СПб.: Питер, 2001.

2. Гаврилова Т.А., Червинская К.Р. Извлечение и структурирование знаний для

экспертных систем. - М.: Радио и связь, 1992.

3. Джексон П. Введение в экспертные системы. - М.: Издат. дом «Вильямс»,

2001.

4. Дж. Ф. Люгер. Искусственный интеллект: стратегии и методы решения

сложных проблем. - М.: Издат. дом «Вильямс», 2003.

5. Ерофеев А.А., Поляков А.О. Интеллектуальные системы управления. – СПб.:

Изд-во СПбГТУ, 1999.

6. Искусственный интеллект. Справочник в 3 томах. – М.: Радио и связь, 1990.

7. Корнеев В.В. и др. Базы занных. Интеллектуальная обработка информации. –

М.: «Нолидж», 2000.

8. Лорьер Ж.-Л. Системы искусственного интеллекта. – М.: Мир, 1991.

9. Любарский Ю.Я. Интеллектуальные информационные системы. – М.: Наука,

1990.

10.Нильсон Н. Принципы искусственного интеллекта. – М.: Радио и связь, 1985.

11.Попов Э. В. Экспертные системы. – М.: Наука, 1987.

12.Уотерман Д. Руководство по экспертным системам. – М.: Мир, 1989.

13.Элти Дж., Кумбс М. Экспертные системы. Концепции и примеры. – М.:

Финансы и статистика, 1987.

72

Page 73: Учебное пособие по CLIPS

Галина Витальевна Пушкарева

СИСТЕМЫ ИСКУССТВЕННОГО ИНТЕЛЛЕКТА:

ПРОГРАММИРОВАНИЕ В СРЕДЕ CLIPS

Учебное пособие

____________________________________________________________________Подписано в печать Формат 60х84 1/16. Бумага офсетная.

Тираж 100 экз. Печ. л. 4,5.Заказ №

____________________________________________________________________

Отпечатано в типографииНовосибирского государственного технического университета

630092, г. Новосибирск, пр. К. Маркса, 20

73