1

我正在使用 Yacc/Flex 编写程序,并且正在使用以下代码(不完全相同,因为我正在混合来自其他文件的代码):

DataType datat;
%union {  
    int integer;  
    char *string;  
    DataType type;  
}

Integer { yylval.type = INTEGER; return INT; }
%type <type> INT
data : INTNUM { yylval.type = INTEGER; }

然后,如果我写这样的东西:

foo : data { bar(yylval.type); }

bar正确获取数据类型INTEGER,但如果我有这个:

foo : data data { ??? }

如何分别获取第一个和第二个成员的yylval.type

非常感谢!

4

2 回答 2

1

我不完全理解您的问题,但在 lex/yacc(或 flex/bison)中,您必须使用以下约定:

  • 使用 $1 来引用第一项的 yylval
  • 使用 $2 来引用第二项的 yylval
  • 使用 $$ 来引用结果(目标)项目的 yylval

例如,如果您要编写一个简单的整数计算器,定义总和的规则将是这样的:

Sum : Term '+' Term
   {
   $$.Value = $1.Value + $3.Value
   }

希望这可以帮助。

于 2010-02-14T15:56:35.830 回答
0

yylval.type 将返回您扫描的最后一个令牌的类型,这可能是被简化为数据的整数,但也可能是它之后的令牌。你不应该直接在 yacc/bison 文件中访问 yylval,因为它不可靠。

相反,您应该使用$1,$2等来访问 Patrick 指出的项目的 YYSTYPE 信息。为了使这个对非终端起作用,你需要%type在 yacc/bison 文件中为它们使用声明,并且这些非终端的规则需要设置$$,例如:

%type <type> data

%%

data : INTNUM { $$ = INTEGER; }

foo : data { bar($1); }

foo : data data { bar($1, $2); }
于 2010-02-19T01:35:58.243 回答