Добавил:
Upload Опубликованный материал нарушает ваши авторские права? Сообщите нам.
Вуз: Предмет: Файл:
Учебник_Final.doc
Скачиваний:
59
Добавлен:
09.11.2019
Размер:
10.39 Mб
Скачать

10.2.4. Переменные

Как и в других языках программирования, в CLIPS для хранения значений используются переменные. В отличие от фактов, которые являются статическими, или неизменными, содержание переменной динамично и изменяется по мере того, как изменяется присвоенное ей значение.

Идентификатор переменной всегда начинается с вопросительного знака, за которым следует ее имя. В общем случае формат переменной выглядит следующим образом: ?<имя переменной>.

Пример.

?sensor

?noun

?color

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

Пример.

(defrule make-quack

(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 подобны глобальным переменным в процедурных языках программирования, но они значительно слабее типизированы (на них не налагаются ограничения хранения данных только одного типа).

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

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 представляет собой мощное средство, позволяющее сравнивать числа, переменные и строки в левой части правила. Он записывается точно так же, как и образцы. Правило может считается выполненным только тогда, когда наряду с совпадением всех образцов, записанных в левой части правила, справедливо и условие, описанное в test.

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

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

где <аргумент_сравнения> – параметр, по которому сравниваются два следующих аргумента.

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

  • eq – равно (сравнивает тип и значение);

  • neq – не равно;

  • = – равно;

  • <> – не равно;

  • >= – больше или равно;

  • > – больше;

  • <= – меньше или равно;

  • < – меньше.

Все аргументы, кроме eq и neq, используются только для сравнения чисел. При интерпретации выражения сравнения считается, что <аргумент_1> стоит слева от <аргумента_сравнения>, а <аргумент_2> – справа.

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

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

Пример.

(defrule addition

(numbers ?x ?y)

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

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

Например:

(defrule addition

(numbers ?x ?y)

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

=>

(printout t "stock ID = " ?ID crlf))

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

CLIPS поддерживает также процедурную парадигму представления знаний, подобную принятой в обычных языках программирования (С, Паскаль). Конструкция deffunction позволяет пользователю определять новые функции. Эти новые функции могут вызываться точно так же, как и встроенные функции CLIPS. Конструкция defmodule позволяет разбивать базу знаний на части.