Имеющиеся классы-операции

  1. BNFSemanticChecker - проверка семантики bnf-грамматики.
  2. BNFFormater - вывод bnf-грамматики.
  3. AlternativesTestGenerator - генерация тестов.

BNFSemanticChecker

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

Кроме того для узлов типа Rule находится значение атрибута ReferenceList (это список ссылок на правила, в правой части которых встречается данное правило).

Семантические требования на BNF.
  1. Каждый использованный нетерминал должен быть определен.
  2. Не должно быть переопределений одного нетерминала.

BNFFormater

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

Имеются две возможности:

  1. Вывести грамматику в плоский файл.
  2. Вывести грамматику в html-виде.

И в плоском файле и в html-виде все комментарии в стиле java удаляются, остаются только комментарии в стиле javadoc.

В html-виде в отдельном окне выводится полный список ссылок на правила в алфавитном порядке. Сама грамматика выводится в другом окне. Перед каждым правилом выводится список правил, которые содержат в своей правой части данное правило, НО этот список будет выведен, ТОЛЬКО если перед запуском BNFFormater'а был запущен BNFSemanticChecker.

Системные свойства.

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

'bnf.file' -- если свойство определено, в указанный файл выводится отформатированная грамматика (плоский вид).

'html.dir' -- если свойство определено, в указанную директорию выводится грамматика в html-виде.

'html.color.background' -- цвет фона html-документа, по умолчанию - белый (white).

'html.color.comment' -- цвет комментариев, по умолчанию - зеленый (green).

'html.color.token' -- цвет терминалов, по умолчанию - синий (navy).

Если не указаны свойства 'bnf.file' и 'html.dir', то выдается подсказка после чего работа заканчивается.


AlternativesTestGenerator

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

Построение тестов по грамматике, заданной с помощью BNF.
Генерация тестов проводится поэтапно. Для каждого правила генерятся тесты, причем сгенерированный тест сразу же передается какому-либо обработчику. Шаги генерации тестов для конкретного правила:

1. Находится цепочка вывода текущего правила из стартового -- основная цепочка. Если правило недостижимо из стартового, выдается предупреждение и тесты для данного правила не генерятся.

2. Генератор тестов идет по построенной цепочке и раскрывает побочные факторы в режиме first, то есть как-нибудь.

3. Дойдя до текущего правила генератор тестов раскрывает его таким образом. Он проходит по всем альтернативам-термам и для каждой выполняет следующие действия:

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

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

Установки и ограничения.

Для того, чтобы не возникало бесконечных циклов, а также, для управления генерацией введены first-глубина, all-глубина и stop-глубина генерации.

Все глубины вычисляются от основной цепочки. First- и all-глубины вычисляются одинаково, если генератор тестов находится в каком-то правиле, то глубина (first- или all-) этого правила равна тому, сколько раз до этого встретилось правило с таким же именем. Stop-глубина -- это количество правил в цепочке от основной цепочки до текущего правила. First-глубина используется при вычислении first-раскрытия, all- и stop-глубины -- при вычислении all-раскрытий.

Если глубина больше или равна заданной, генератор тестов считает раскрытие данного правила невозможным и делает откат.

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

Stop- и all-глубины взаимодействуют следующим образом: если stop-глубина не 0, то учитываются обе глубины, если stop-глубина нулевая, то считается, что она равна бесконечности, то есть она попросту игнорируется.

Запуск генератора.
Запускать генератор следует ТОЛЬКО после обработки грамматики BNFSemanticChecker'ом см.также здесь.

Перед запуском следует установить имя стартового правила грамматики ('start.rule'), файл лексем ('lexeme.file') и обработчик тестов ('processor'). Если одно из этих свойств не установлено, об этом будет выдано предупреждение, после чего работа прервется. См. также системные свойства.

Файл лексем содержит варианты раскрытий лексем из грамматики в следующем формате:

<имя_лексемы> "вариант1" "вариант2" ...
<имя_лексемы> "вариант1" "вариант2" ...
 .   .   .
<имя_лексемы> "вариант1" "вариант2" ...

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

Критические факторы системы.

Оперативная память не является критическим фактором данной системы. Количество используемой оперативной памяти слабо зависит от грамматики, больше зависит от устанавливаемых глубин, так как при больших глубинах возрастает глубина стека вызовов методов.

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

Для улучшения ситуации можно воспользоваться подходящим обработчиком тестов.

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

Cистемные свойства.

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

'start.rule' -- имя стартового правила. Должно быть установлено обязательно.

'lexeme.file' -- путь до файла с лексемами. Должен быть установлен обязательно.

'processor' -- способ обработки теста на выходе. Используемый обработчик должен быть зарегистрирован под каким-либо именем в том же файле, что и AlternativesTestGenerator. Свойство 'processor' -- это зарегистрированное имя обработчика (см. здесь). Передаваемый обработчику тест является объектом класса Sentence. Если данное свойство не установлено, то происходит просто подсчет тестов.

'first.depth' -- глубина поиска первого попавшегося раскрытия нетерминала. Рекомендуется ставить 2 и больше (по умолчанию -- 2). Если при установленной глубине нетерминал не раскрывается, то об этом будет сообщено в самом начале работы, но работа не прервется, генератор будет пытаться строить то что можно.

'all.depth' -- глубина режима all, вычисляется так: для текущего нетерминала A считается количество нетерминалов с тем же именем A в цепочке от целевого нетерминала до текущего. По умолчанию -- 2.

'stop.depth' -- глубина режима all, вычисляется так: для текущего нетерминала считается количество нетерминалов в цепочке от целевого нетерминала до текущего. Если установлена в 0, то считается равной бесконечности (по умолчанию -- 0), если установлена не в 0, то учитывается вместе с 'all.depth', то есть обрыв цепочек идет по обеим глубинам.

'order.file' -- установка правил, для которых будут генериться тесты. Если 'order.file' не установлен, то генерация осуществляется для всех правил. Иначе имена нужных правил будут считываться из файла, путь до которого устанавливается свойством 'order.file'. Формат этого файла следующий:

    <имя_правила_как_оно_записано_в_bnf_файле>
    <имя_правила_как_оно_записано_в_bnf_файле>
     .     .     .
    <имя_правила_как_оно_записано_в_bnf_файле>
Каждое имя должно быть записано в отдельной строчке. Пустые строчки игнорируются.

'first.realization.file' -- путь до файла, содержащего first-раскрытия нетерминалов. Файл имеет следующий формат:

    <имя_правила_как_оно_записано_в_bnf_файле>  <какое-либо_раскрытие_данного_правила>
    <имя_правила_как_оно_записано_в_bnf_файле>  <какое-либо_раскрытие_данного_правила>
     .     .     .
    <имя_правила_как_оно_записано_в_bnf_файле>  <какое-либо_раскрытие_данного_правила>
Если файл уже существует, то вся информация будет считана и, если для каких-то нетерминалов не найдены first-раскрытия, недостающая информация будет сгенерирована. Если файла не существует, то first-раскрытия будут сгенерированы, а затем записаны в указанный файл. Если данное свойство не определено, то запись производится не будет. Для генерации first-раскрытий используется FirstGenerator.

'first.test' -- номер первого теста, который будет передан обработчику. По умолчанию -- 0.

'test.quantity' -- количество тестов, которые будут переданы обработчику, начиная с теста с номером 'first.test'. Если 0, то считается равным бесконечности. По умолчанию -- 0.


Софья Зеленова
Last modified: Mon Feb 26 12:58:04 MSK 2001