2015-10-08 4 views
0

Я написал простую C-подобную грамматику в Bison, и у меня есть странная проблема.Bison: Получение/сохранение значений nonterminals

В следующем правиле:

declaration:  "identifier" length init_values      
        {symbolTable.add($3,$4,$5);} 

Я хочу, чтобы получить Int значения length и init_values, которые нетерминалы, хранить их в таблице символов. identifier - это токен, и его буквальное значение сохраняется правильно. Тем не менее, я получаю некоторые целые значения, такие как 66236273 для других символов.

нетерминальных правил:

length:    "number" {};       
init_values:  "number" {}; 

Я попытался с помощью токенов непосредственно вместо нетерминалов, но синтаксический анализатор не может различать number и length и так далее. Он просто проанализировал все целые числа как number, что и привело к его сбою.

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

+0

Почему вы используете $ 3, $ 4, $ 5? В правой части этого правила есть только три символа, поэтому они должны быть. $ 1, $ 2, $ 3. – rici

ответ

0

Не видя больше своих определений в грамматике и сканере, трудно точно сказать, что вы делаете неправильно. Но вот несколько предложений:

  1. {symbolTable.add($3,$4,$5);} неправилен с предоставленным грамматическим правилом; он должен быть {symbolTable.add($1,$2,$3);}, поскольку значения правого поля подсчитываются слева направо, начиная с $1.

  2. Предполагая, что "identifier" является char * и "integer" является long (или некоторые такие), то важно, чтобы все терминалы и нетерминалы быть объявлены с правильным значением тега семантической. См. the bison manual.

  3. Там нет необходимости length: "number" {};, но так как действие по умолчанию эффективно $$ = $1, он не должен делать никакого вреда до тех пор, как length и "number" объявляются с помощью правильного типа тега. Я понятия не имею, что вы подразумеваете под «Я пытался использовать токены непосредственно вместо нетерминалов», если это не значит, что вы пробовали declaration: "identifier" "number" "number"; нет причин, по которым это не должно работать (пока объявления типа верны).

  4. Если вы передаете строки символов в yylval, убедитесь, что вы копируете строки. yylval.str = yytext; не подходит, и вы попадете в неприятности. См. this FAQ entry.

Смежные вопросы