Операционная система UNIX. Руководство программиста


Действия


С каждым грамматическим правилом пользователь может связать действия, которые будут выполняться при применении правила. Действия могут возвращать значения и получать значения, возвращенные предыдущими действиями. Кроме того, если требуется, лексический анализатор может возвращать значения лексем.

Действие - это произвольный оператор на языке C. Следовательно, в действии можно выполнять операции ввода/вывода, вызывать подпрограммы, изменять значения массивов и переменных. Действие задается одним или несколькими операторами в фигурных скобках, { и }. Например, конструкции

A : '(' B ')' { hello (1, "abc"); } ;

и

XXX : YYY ZZZ { (void) printf ("сообщение\n"); flag = 25; } ;

являются грамматическими правилами с действиями.

Для организации взаимосвязи между действиями и процедурой разбора используется знак $ (доллар). Псевдопеременная $$ представляет значение, возвращаемое завершенным действием. Например, действие

{$$ = 1;}

возвращает значение 1; в сущности, это все, что оно делает.

Чтобы получать значения, возвращаемые предыдущими действиями и лексическим анализатором, действие может использовать псевдопеременные $1, $2, ... $n. Они обозначают значения, возвращаемые компонентами от 1-го до n-го, стоящими в правой части правила; компоненты нумеруются слева направо. В случае правила

A : B C D ;

$2 принимает значение, возвращенное C, а $3 - значение, возвращенное D.

Пример с правилом

expr : '(' expr ')' ;

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

expr : '(' expr ')' { $$ = $2; } ;

По умолчанию значение правила равно значению первого компонента в нем ($1). Поэтому грамматические правила вида

A : B ;

зачастую не требуют явного указания действия. В предыдущих примерах действия всегда выполнялись в конце применения правила. Иногда же бывает желательно получить управление до того, как правило применено полностью. yacc позволяет писать действие в середине правила так же, как и в конце. Считается, что такое действие возвращает значение, доступное действиям справа от него посредством обычного механизма $. В свою очередь, оно имеет доступ к значениям, возвращаемым действиями слева от него. Таким образом, в правиле, указанном ниже, результатом действия является присваивание переменной x значения 1, а переменной y - значения, которое возвращает C.




Начало  Назад  Вперед