Добавил:
Upload Опубликованный материал нарушает ваши авторские права? Сообщите нам.
Вуз: Предмет: Файл:
Распечатка. Шпоры.doc
Скачиваний:
10
Добавлен:
28.04.2019
Размер:
644.61 Кб
Скачать

Вопрос 13

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

Синтаксический анализатор расчленяет исходную программу на составные части, формирует ее внутреннее представление, заносит информацию в таблицу символов и другие таблицы. При этом производится полный синтаксический и, по возможности, семантический контроль программы. Фактически, это - синтаксически управляемая программа. При этом обычно стремятся отделить синтаксис от семантики насколько это возможно - когда синтаксический анализатор распознает конструкцию исходного языка, он вызывает семантическую процедуру, которая контролирует эту конструкцию, заносит информацию куда надо, проверяет на дублирование описания переменных, проверяет соответствие типов и т.п.

Предложения исходной программы обычно записываются в инфиксной форме. Однако эта привычная форма, в которой оператор записывается между операндами, является совершенно не пригодной для автоматического вычисления. Дело в том, что необходимо постоянно помнить о приоритетах операторов, "забегая" при анализе выражения "вперед". К тому же очень усложняют жизнь применяемые скобки, определяющие очередность вычислений. Альтернативой инфиксной форме является польская форма записи (в честь польского математика Лукасевича): постфиксная и префиксная. Обычно под польской формой понимают именно постфиксную форму записи. Кроме того, используются и такие внутренние формы представления исходной программы, как дерево (синтаксическое) и тетрады.

Вопрос 14

Общие принципы работы табличных распознавателей

Табличные распознаватели используют для построения цепочки вывода КС-грамматики другие принципы, нежели МП-автоматы. Как и МП-автоматы, они получают на вход цепочку входных символов  = a1a2…an, VT*, || = n, а по­строение вывода основывают на правилах заданной КС-грамматики G(VT,VN,P,S). Принцип их работы заключается в том, что искомая цепочка вывода строится не сразу — сначала на основе входной цепочки порождается некоторое промежу­точное хранилище информации объема n*n (промежуточная таблица), а потом уже на его основе строится вывод.

Табличные алгоритмы обладают полиномиальными характеристиками требуе­мых вычислительных ресурсов в зависимости от длины входной цепочки. Для произвольной КС-грамматики G(VT,VN,P,S) время выполнения алгоритма Тэ имеет кубическую зависимость от длины входной цепочки, а необходимый объ­ем памяти Мэ — квадратичную зависимость от длины входной цепочки: Тэ = О(n3) и Мэ = O(n2). Квадратичная зависимость объема необходимой памяти от длины входной цепочки напрямую связана с использованием проме­жуточного хранилища данных.

Табличные распознаватели универсальны — они могут быть использованы для распознавания цепочек, порожденных с помощью произвольной КС-грамматики (возможно, саму грамматику первоначально потребуется привести к заданному виду, но это не ограничивает универсальности алгоритмов). Кроме того, табличные распознаватели — это самые эффективные с точки зрения требуемых вычислительных ресурсов универсальные алгоритмы для распознавания цепочек КС-языков.

Хотя табличные распознаватели и являются самыми эффективными среди универсаль­ных распознавателей, тем не менее они не находят широкого применения. Дело в том, что полиномиальная зависимость требуемых вычислительных ресурсов от длины входной цепочки символов является неудовлетворительной для компиляторов (длины входных цепочек — тысячи и десятки тысяч символов). Поэтому практически всегда используют­ся не универсальные, а более узкие, специализированные алгоритмы распознавателей, которые имеют обычно линейную зависимость требуемых вычислительных ресурсов от длины входной цепочки символов К универсальным алгоритмам прибегают только то­гда, когда специализированный распознаватель построить не удается.

Алгоритм Кока—Янгера—Касами

Алгоритм Кока—Янгера—Касами для заданной грамматики G(VT,VN,P,S) и цепочки входных символов ,  = a1a2…an, VT*, || = n строит таблицу Tn*n, такую, что AVN: AT[i,j], тогда и только тогда, если А+аi...ai+j-1. Таким образом, элементами таблицы Tn*n являются множества нетерминальных символов в алфавита VN.

Тогда существованию вывода S* соответствует условие ST[1,n].

При условии существования вывода по таблице Tn*n можно найти всю полную цепочку вывода S*.

Для построения вывода по алгоритму Кока—Янгера—Касами грамматика G(VT,VN,P,S) должна быть в нормальной форме Хомского. Поскольку, как было показано выше, любую произвольную КС-грамматику можно преобразовать в нормальную форму Хомского, это не накладывает дополнительных ограничений на применимость данного алгоритма.

Алгоритм Кока—Янгера—Касами фактически состоит из трех вложенных циклов. Поэтому ясно, что время выполнения алгоритма имеет кубическую зависимость от длины входной цепочки символов. Таблица Tn*n, используемая для хранения промежуточных данных в процессе работы алгоритма, является таблицей множеств. Очевидно, что требуемый для ее хранения объем памяти имеет квадратичную зависимость от длины входной цепочки символов.

Сам алгоритм Кока—Янгера—Касами можно описать следующим образом:

Шаг1.

Цикл для j от 1 до n

Т[1,j] := {А |  АajР} - в T[1,j] включаются все нетерминальные символы для которых в грамматике G существует правило Aaj

Конец цикла для j

Шаг 2.

Цикл для i от 2 до n

Цикл для j от 1 до n-i+1

T[1,j] = .

Цикл для k от 1 до i-1

T[1,j] := Т[1,j]  {А |  АВС  Р, BT[k.j], CT[i-k, j+k]}

Конец цикла для k

Конец цикла для j

Конец цикла для i

Результатом работы алгоритма будет искомая таблица Tn*n. Для проверки суще­ствования вывода исходной цепочки в заданной грамматике остается только про­верить условие ST[1,n].

Если вывод существует, то необходимо получить цепочку вывода. Для этого существует специальная рекурсивная процедура R. Она выдает последователь­ность номеров правил, которые нужно применить, чтобы получить цепочку вы­вода. Ее можно описать следующим образом: R(i,j,A), где AVN.

1. Если j=1 и существует правило Ааi, то выдать номер этого правила.

2. Иначе (если j > 1) возьмем k как наименьшее из чисел, для которых  АВХ  Р, BT[k,j], CT[i-k,j+k] (таких правил может быть несколько, для определенности берем наименьшее k). Пусть правило АВС имеет номер m. Тогда нужно выдать этот номер m, потом вызвать сначала R(i,k,B), а затем — R(i-k,j+k,C).

Для получения всей последовательности номеров правил нужно вызвать R(1,n,S).

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

На основании последовательности номеров правил, полученной с помощью алго­ритма Кока—Янгера—Касами и рекурсивной процедуры R, можно построить лево­сторонний вывод для заданной грамматики G(VT,VN,P,S) и цепочки входных сим­волов . Таким образом, с помощью данного алгоритма решается задача разбора.