Многопроходный компилятор
— Многопроходный компилятор это тип компилятора , который несколько раз обрабатывает исходный код или абстрактное синтаксическое дерево программы. В этом отличие от однопроходного компилятора , который обходит программу только один раз. Каждый проход принимает результат предыдущего прохода в качестве входных данных и создает промежуточный выходной результат. Таким образом, (промежуточный) код улучшается шаг за шагом, пока последний проход не создаст окончательный код.
Многопроходные компиляторы иногда называют широкими компиляторами . [1] имея в виду больший объем проходов: они могут «видеть» всю компилируемую программу, а не только небольшую ее часть. Таким образом, более широкая область действия, доступная этим компиляторам, позволяет лучше генерировать код (например, меньший размер кода, более быстрый код) по сравнению с результатами однопроходных компиляторов за счет увеличения времени компилятора и потребления памяти. Кроме того, некоторые языки не могут быть скомпилированы за один проход из-за особенностей их конструкции.
Типичный многопроходный компилятор [ править ]
Лексический анализ [ править ]
Этот этап многопроходного компилятора заключается в удалении ненужной информации из исходной программы, которую синтаксический анализ не сможет использовать или интерпретировать. Нерелевантная информация может включать в себя такие вещи, как комментарии и пробелы. Помимо удаления ненужной информации, лексический анализ определяет лексические лексемы языка. Этот шаг означает, что предварительное объявление обычно не требуется, если используется многопроходный компилятор. На этом этапе основное внимание уделяется разбиению последовательности символов на токены с такими атрибутами, как вид, тип, значение и, возможно, другими.
Синтаксический анализ [ править ]
Синтаксический анализ отвечает за изучение синтаксических правил языка (часто в виде контекстно-свободной грамматики ) и построение некоторого промежуточного представления языка. Примером такого промежуточного представления может быть что-то вроде абстрактного синтаксического дерева или ориентированного ациклического графа .
Семантический анализ [ править ]
Семантический анализ берет представление, полученное в результате синтаксического анализа, и применяет к нему семантические правила, чтобы убедиться, что программа соответствует требованиям семантических правил языка. Например, в приведенном ниже примере на этапе семантического анализа, если язык требует, чтобы условия о том, являются ли операторы логическими выражениями, cond будет проверено по типу, чтобы убедиться, что это будет допустимое логическое выражение.
if (cond) {
...
} else {
...
}
Помимо выполнения семантического анализа на этом этапе компиляции часто создаются таблицы символов , помогающие генерировать код.
Генерация кода [ править ]
Этот заключительный этап типичного компилятора преобразует промежуточное представление программы в исполняемый набор инструкций (часто ассемблер ). Этот последний этап — единственный этап компиляции, зависящий от машины. На этом этапе компиляции также можно провести оптимизацию , которая сделает программу более эффективной.
Другие этапы компилятора включают фазу промежуточной генерации кода, которая происходит перед генерацией кода, и фазу оптимизации кода, которая может иметь место при написании исходной программы, или после фазы генерации промежуточного кода, или после фазы генерации кода.
Преимущества многопроходных компиляторов [ править ]
Машинно-независимый : поскольку несколько проходов включают в себя модульную структуру, а генерация кода отделена от других шагов компилятора, проходы можно повторно использовать для различного оборудования/машин.
Более выразительные языки : несколько проходов устраняют необходимость в предварительных объявлениях, позволяя элегантно реализовать взаимную рекурсию. Яркие примеры языков, требующих предварительных объявлений из-за требования компиляции за один проход, включают C и Pascal , тогда как в Java нет предварительных объявлений.
Ссылки [ править ]
- ^ Грюн, Дик; ван Реувейк, Кес; Баль, Анри; Джейкобс, Сериэль; Лангендоен, Коэн (2012). Современный дизайн компилятора (второе изд.). Амстердам, Нидерланды: Springer. п. 27. ISBN 978-1-4939-4472-9 .
- Борнат, Ричард , Понимание и написание компиляторов: Руководство «Сделай сам» , Macmillan Publishing, 1979. ISBN 0-333-21732-2
- Бент Томсен, «Языки и компиляторы SProg и переводчики» , факультет компьютерных наук, Ольборгский университет