Грамматика LL(1) Висячий else и общий левый префикс

Я полагаю, что каждый, кто читает его, знаком с двусмысленностью else. Поэтому я пропущу объяснение. Я нашел в книге компиляторов (книге дракона) недвусмысленную грамматику, которая представляет IF и ELSE. Вот.

stmt->matched_stmt | open_stmt
matched_stmt->if exp then matched_stmt else matched_stmt | other
open_stmt->if exp then stmt | if exp then matched_stmt else open_stmt

Проблемы:

open_stmt->если exp то stmt | если exp, то matched_stmt иначе open_stmt

Чтобы заставить грамматику, которую я работаю над грамматикой LL(1), мне нужно исключить левый общий префикс, и в этом случае левый общий префикс:

если эксп, то

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

stmt->matched_stmt | open_stmt
matched_stmt->if exp then matched_stmt else matched_stmt | other
open_stmt->if exp thenO'
O'->stmt | matched_stmt else open_stmt

Что неоднозначно, может ли кто-нибудь помочь мне сделать его не двусмысленным и без общего левого префикса? большое спасибо


person Bruno Braga    schedule 29.09.2015    source источник


Ответы (1)


Я не верю, что возможно написать грамматику LL(1), которая будет обрабатывать висячие else, хотя написать анализатор рекурсивного спуска, который это делает, тривиально.

В синтаксическом анализаторе рекурсивного спуска, когда вы выполнили синтаксический анализ первого оператора после выражения, если вы видите else, вы продолжаете производство. В противном случае вы закончили синтаксический анализ оператора if. Другими словами, вы просто жадно анализируете предложения else.

Но этот алгоритм нельзя выразить в виде CFG, и я всегда предполагал, что невозможно написать однозначную LL(1) CFG, которая обрабатывает висячие elses, потому что, когда вы достигаете начала S1 в

if E then S1 ...

вы все еще не знаете, частью какого производства это является. На самом деле вы ничего не знаете, пока не дойдете до конца S1, что, безусловно, слишком поздно для принятия решения LL(k), независимо от того, насколько велико k.

Однако в этом объяснении много маханий руками, и я никогда не находил его полностью удовлетворительным. Так что я был рад взять свою потрепанную копию книги Dragon (издание 1986 года) и прочитать на странице 192 («Грамматики LL(1)» в разделе 4.4, «Грамматики сверху вниз»), что грамматика 4.13 (if- тогда-необязательная-иначе грамматика) «вообще не имеет грамматики LL (1)».

Следующий абзац заканчивается разумным советом: «если доступен генератор синтаксического анализатора LR, можно автоматически получить все преимущества прогнозирующего синтаксического анализа и приоритета операторов». Моя заметка на полях (примерно 1986 года, я полагаю) гласит: «Так почему я только что изучил всю эту главу????»; сегодня я был бы склонен быть более великодушным с авторами книги о Драконе, но не до такой степени, чтобы предлагать кому-либо на самом деле использовать генератор синтаксических анализаторов, который, по крайней мере, не такой мощный, как LALR( 1) генератор парсеров.

person rici    schedule 30.09.2015
comment
Странно думать, что грамматика, которая должна обрабатывать if и else, не может быть LL(1). Я пробовал много вещей, но каждый раз моя таблица синтаксического анализа становится неоднозначной (два разных производства идут к одному и тому же терминальному значению). Я думаю, что это все, спасибо вам большое. - person Bruno Braga; 30.09.2015
comment
@BrunoBraga Почему это должно быть LL (1)? LL(1) — очень ограниченный набор грамматик; есть много конструкций, которые не могут быть адекватно выражены в LL(1). Простая левоассоциативная грамматика выражений не может быть правильно написана на LL(1); вам нужно перенастроить результирующее право-ассоциативное дерево синтаксического анализа, чтобы получить правильную ассоциативность. На практике двусмысленность if-else не является серьезной, потому что (как я уже упоминал) синтаксический анализатор рекурсивного спуска может легко принять правильное решение и, таким образом, избежать неоднозначности, и большинство генераторов синтаксических анализаторов LL обработают это правильно. Но лично я иду на разбор LR. - person rici; 30.09.2015
comment
Нет причин, мне просто интересно, возможно ли это или нет, так как в данный момент я изучаю грамматики LL(1). - person Bruno Braga; 30.09.2015