Фазы компилятора? - PullRequest
       31

Фазы компилятора?

4 голосов
/ 05 марта 2011

На каком этапе компиляции распознаются ключевые слова языка программирования?

Я как-то запутался между

  1. Лексическим анализом.
  2. Разбор программы.

Однажды я написал лексер на C, используя регулярные выражения, но он распознал main() в int main(void) также как ключевое слово.

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

Ответы [ 5 ]

3 голосов
/ 07 марта 2011

В этом году мне пришлось создать простой компилятор как проект, для которого я использовал Java.Распознавание ключевых слов было сделано по лексическому анализу.На этом этапе я читал язык ввода и создавал токен с типом (для ключевых слов тип был variable_declaration) и его значением. У меня также были разные типы для каждого случая, такие как идентификатор, константа, операция умножения, операция добавления и т. Д. Затем эти токены передавалисьв очередь и затем в парсер, который проверяет грамматику и создает двоичное дерево, которое затем используется для создания языка вывода.

3 голосов
/ 05 марта 2011

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

Statement ::= 'IF' Expr 'THEN' Expr

Если я не классифицирую IF и THEN в их собственные типы токенов, тогда мой парсер не смог написать оператор, подобный приведенному выше.

1 голос
/ 09 марта 2011

Традиционно ключевые слова распознаются лексером (что оставляет вас с языком, состоящим из фиксированного набора ключевых слов).Но, конечно, вы можете сделать это во время синтаксического анализа.Вы даже можете полностью избавиться от своего лексера, используя один из многочисленных методов анализа без лексера (например, PEGs ).Это может помочь вам избежать путаницы.

1 голос
/ 05 марта 2011

Очень сильно зависит от определения, особенно от того, где вы рисуете линии между сканером, токенизатором, лексером и анализатором. Так как это домашняя работа, и это правильно, только если ваш проф. говорит, что это правильно: взгляните на определения, приведенные в вашем материале для чтения.

Относительно main (): Вы определенно можете сказать, что main (), как и все другие функции, не является ключевым словом, но, тем не менее, является токеном. Токенайзер распознает, что подстрока «main» является одним токеном, и синтаксический анализатор устанавливает его относительно его частей «(...)» и «{...}». Далее, для main () парсер автоматически сгенерирует точку входа в программу.

1 голос
/ 05 марта 2011

Это будет лексический анализ.

В некоторых языках есть «специальные» идентификаторы и ключевые слова.Они часто добавляются в таблицу идентификаторов и распределяются известные значения идентификаторов констант до начала анализа, чтобы их можно было легко обнаружить.Однако они обычно не имеют особого значения для синтаксического анализатора - они должны быть обнаружены в абстрактном синтаксическом дереве (AST) после синтаксического анализа.

Например, взгляните на отчет по языку Оберона ...

http://www -old.oberon.ethz.ch / oreport.html

Не рекомендация по языку - просто легкодоступная и простая языковая спецификация (очень в стиле Wirths).

В любом случае, раздел «Словарь и представление» содержит список «операторов и разделителей», включая то, что большинство людей распознало бы как ключевые слова.Они будут распознаваться лексическим анализатором.

В разделе «Объявления и правила области действия» есть список предопределенных идентификаторов, таких как «ABS» и «BOOLEAN».Я не достаточно знаком с Обероном, чтобы быть уверенным, но если бы я написал компилятор, есть хороший шанс, что я просто предварительно инициализировал бы таблицу нормальных идентификаторов, чтобы включить эти предопределенные идентификаторы.

В C«main» в большинстве случаев является просто другой функцией.Компилятор может или не может рассматривать его как особый.Вполне возможно, что единственное «особенное» в этом то, что код запуска, который связывается с вашим конечным исполняемым файлом, вызывает эту функцию.

...