我对Yacc有疑问。这是我用于解析C语言语法的Yacc代码。请注意,下面的代码只是完整代码的一些相关部分:
%token IDENTIFIER I_CONSTANT F_CONSTANT STRING_LITERAL FUNC_NAME SIZEOF
%token PTR_OP INC_OP DEC_OP LEFT_OP RIGHT_OP LE_OP GE_OP EQ_OP NE_OP
%token AND_OP OR_OP MUL_ASSIGN DIV_ASSIGN MOD_ASSIGN ADD_ASSIGN
%token SUB_ASSIGN LEFT_ASSIGN RIGHT_ASSIGN AND_ASSIGN
%token XOR_ASSIGN OR_ASSIGN
%token TYPEDEF_NAME ENUMERATION_CONSTANT
%token TYPEDEF EXTERN STATIC AUTO REGISTER INLINE
%token CONST RESTRICT VOLATILE
%token BOOL CHAR SHORT INT LONG SIGNED UNSIGNED FLOAT DOUBLE VOID
%token COMPLEX IMAGINARY
%token STRUCT UNION ENUM ELLIPSIS
%token CASE DEFAULT IF ELSE SWITCH WHILE DO FOR GOTO CONTINUE BREAK RETURN
%token ALIGNAS ALIGNOF ATOMIC GENERIC NORETURN STATIC_ASSERT THREAD_LOCAL
%union{
char* a;
char* b;
}
%type <a>IDENTIFIER
%type <a>SIGNED UNSIGNED
%type <a>INT CHAR DOUBLE FLOAT LONG SHORT
%type <b>EXTERN STATIC AUTO REGISTER
%%
declaration
: declaration_specifiers ';'
| declaration_specifiers init_declarator_list ';' { printf("semicolon:%s\n", $<a>3);}
| static_assert_declaration
;
declaration_specifiers
: storage_class_specifier declaration_specifiers
| storage_class_specifier
| type_specifier declaration_specifiers
| type_specifier
| type_qualifier declaration_specifiers
| type_qualifier
| function_specifier declaration_specifiers
| function_specifier
| alignment_specifier declaration_specifiers
| alignment_specifier
;
init_declarator_list
: init_declarator
| init_declarator_list ',' init_declarator {printf("The comma:%s\n",$<a>2);}
;
type_specifier
: VOID {printf("type_specifier:%s\n",$<a>1);}
| CHAR {printf("type_specifier:%s\n",$<a>1);}
| SHORT {printf("type_specifier:%s\n",$<a>1);}
| INT {printf("type_specifier:%s\n",$<a>1);}
| LONG {printf("type_specifier:%s\n",$<a>1);}
| FLOAT {printf("type_specifier:%s\n",$<a>1);}
| DOUBLE {printf("type_specifier:%s\n",$<a>1);}
| SIGNED {printf("type_specifier:%s\n",$<a>1);}
| UNSIGNED {printf("type_specifier:%s\n",$<a>1);}
| BOOL {printf("type_specifier:%s\n",$<a>1);}
| COMPLEX {printf("type_specifier:%s\n",$<a>1);}
| IMAGINARY /* non-mandated extension */ {printf("type_specifier:%s\n",$<a>1);}
| atomic_type_specifier {printf("type_specifier:%s\n",$<a>1);}
| struct_or_union_specifier {printf("type_specifier:%s\n",$<a>1);}
| enum_specifier {printf("type_specifier:%s\n",$<a>1);}
| TYPEDEF_NAME {printf("type_specifier:%s\n",$<a>1);}
;
declarator
: pointer direct_declarator
| direct_declarator
;
direct_declarator
: IDENTIFIER {printf("The identifier: %s\n", $<a>1);}
| '(' declarator ')'
| direct_declarator '[' ']'
| direct_declarator '[' '*' ']'
| direct_declarator '[' STATIC type_qualifier_list assignment_expression ']'
| direct_declarator '[' STATIC assignment_expression ']'
| direct_declarator '[' type_qualifier_list '*' ']'
| direct_declarator '[' type_qualifier_list STATIC assignment_expression ']'
| direct_declarator '[' type_qualifier_list assignment_expression ']'
| direct_declarator '[' type_qualifier_list ']'
| direct_declarator '[' assignment_expression ']'
| direct_declarator '(' parameter_type_list ')'
| direct_declarator '(' ')'
| direct_declarator '(' identifier_list ')'
;
这是我的Lex代码对应Yacc代码(同样,这些只是相关部分):
"int" { yylval.a=strdup(yytext); return(INT); } /* Data Type*/
"long" { yylval.a=strdup(yytext); return(LONG); }
"char" { yylval.a=strdup(yytext); return(CHAR); }
"short" { yylval.a=strdup(yytext); return(SHORT); }
"signed" { yylval.a=strdup(yytext); return(SIGNED); }
"double" { yylval.a=strdup(yytext); return(DOUBLE); }
"unsigned" { yylval.a=strdup(yytext); return(UNSIGNED); }
"float" { yylval.a=strdup(yytext); return(FLOAT); }
";" { yylval.a=strdup(yytext); return ';'; }
"," { yylval.a=strdup(yytext); return ','; }
我的问题是当我输入命令输入时,例如:
int a,b;
应该打印:
type_specifier:int
The identifier: a
The comma:,
The identifier:b
semicolon:;
但我的输出是
type_specifier:int
The identifier: a
The identifier: b
The comma:,
semicolon:;
我应该怎么做才能完成例行程序:{printf("The comma:%s\n",$<a>2);}
在两个IDENTIFIER {printf("The identifier: %s\n", $<a>1);}
之间激活
参考资料 (原始版本)
答案 0 :(得分:0)
在您完成printf
的解析之前,您的init_declarator
不会执行。试试这个:
| init_declarator_list ',' {printf("The comma:%s\n",$<a>2);} init_declarator