使用flex和Bison的解析器

使用flex和Bison的解析器,bison,Bison,我正在使用flex和bison实现一个解析器。我遇到的一个问题是,如何向解析器提供独立flex文件的标记。当我试图编译我的parser.tab.c时,它抱怨“对yylex的未定义引用”。 然后,我尝试在编译时设置-d选项,并将头文件包含到flex文件中 我只是想知道使用flex和bison(以及编译和运行的相关命令)的正确步骤,我正在使用gcc编译器 很多 /* Token Scanner for C- language */ %{ #include <stdio.h> #inc

我正在使用flex和bison实现一个解析器。我遇到的一个问题是,如何向解析器提供独立flex文件的标记。当我试图编译我的
parser.tab.c
时,它抱怨
“对yylex的未定义引用”
。 然后,我尝试在编译时设置-d选项,并将头文件包含到flex文件中

我只是想知道使用flex和bison(以及编译和运行的相关命令)的正确步骤,我正在使用gcc编译器

很多

/* Token Scanner for C- language */

%{

#include <stdio.h>
#include <stdlib.h>
#include "parser.tab.h"
extern YYSTYPE yylval;



%}



digit                [0-9]
letter               [a-zA-Z]
NUM              {digit}+
ID               {letter}+
KEY_WORD             else|if|int|return|void|while
PLUS_OPERATOR            "+"
MINUS_OPERATOR               "-"
MUL_OPERATOR                 "*"
DIV_OPERATOR                 "/"
LESS_THAN_OPERATOR           "<"
LESS_THAN_OR_EQUAL_OPER      "<="
GREATER_THAN_OPERATOR            ">"
GREATER_THAN_OR_EQUAL_OPERATOR   ">="
EQUAL_OPERATOR           "="
OBJ_EQUAL_OPERATOR           "=="
NOT_EQUAL_OPERATOR           "!="
COMMA_SYMBOL             ","
SEMI_COLON_SYMBOL        ";"
LEFT_BRAC_SYMBOL         "("
RIGHT_BRAC-SYMBOL        ")"
LEFT_SQUARE_BRAC_SYMBOL          "["
RIGHT_SQUARE_BRAC_SYMBOL     "]"
LEFT_CURLY_BRAC_SYMBOL       "{"
RIGHT_CURLY_BRAC_SYMBOL      "}"
LEFT_COMMENT             "/*"
RIGHT_COMMENT            "*/"
ELSE                "else"
IF              "if"
INT             "int"
RETURN              "return"
VOID                "void"
WHILE               "while"

SYMBOL               "+"|"-"|"*"|"/"|"<"|"<="|">"|">="|"=="|"!="|"="|";"|","|"("|")"|"{"|"}"|"["|"]"|"/*"|"*/"      

WHITESPACE                [ \t\n]+
COMMENT               "/*"(.)*({WHITESPACE})*(.)*"*/"

ERROR1                {NUM}(({ID}|{KEY_WORD})|{NUM})+
ERROR2                {ID}(({NUM}|{KEY_WORD})|{ID})+
ERROR3                {KEY_WORD}(({ID}|{NUM})|{KEY_WORD})+  

ERROR                 ERROR1|ERROR2|ERROR3


%%


{NUM}            {
                return NUM;
                }

{ELSE}               {
                return ELSE;
                        }

{IF}             {
                return IF;
                        }

{INT}            {
                return INT;
                        }

{RETURN}             {
                return RETURN;
                        }

{VOID}               {
                return VOID;
                        }

{WHILE}              {
                return WHILE;
                        }


{ID}                {
                return ID;
                }

{PLUS_OPERATOR}      {
                return PLUS_OPERATOR;
                     }

{MINUS_OPERATOR}    {
                return MINUS_OPERATOR;
                     }

{MUL_OPERATOR}          {
                return MUL_OPERATOR;
                        }
{DIV_OPERATOR}          {
                return DIV_OPERATOR;
                        }
{LESS_THAN_OPERATOR}    {
                return LESS_THAN_OPERATOR;
                        }
{LESS_THAN_OR_EQUAL_OPER}   {
                return LESS_THAN_OR_EQUAL_OPER;
                        }

{GREATER_THAN_OPERATOR}  {
                return GREATER_THAN_OPERATOR;
                        }

{GREATER_THAN_OR_EQUAL_OPERATOR}   {
                return GREATER_THAN_OR_EQUAL_OPERATOR;
                        }
{EQUAL_OPERATOR}        {
                return EQUAL_OPERATOR;
                        }
{OBJ_EQUAL_OPERATOR}    {
                return NOT_EQUAL_OPERATOR;
                        }
{NOT_EQUAL_OPERATOR}    {
                return NOT_EQUAL_OPERATOR;
                        }
{COMMA_SYMBOL}  {
                return COMMA_SYMBOL;
                        }
{SEMI_COLON_SYMBOL}   {
                return SEMI_COLON_SYMBOL;
                        }

{LEFT_BRAC_SYMBOL}   {
                return LEFT_BRAC_SYMBOL;
                        }
{RIGHT_BRAC-SYMBOL}  {
                return RIGHT_BRAC_SYMBOL;
                        }

{LEFT_SQUARE_BRAC_SYMBOL}   {
                return LEFT_SQUARE_BRAC_SYMBOL;
                        }
{RIGHT_SQUARE_BRAC_SYMBOL}  {
                return RIGHT_SQUARE_BRAC_SYMBOL;
                        }
{LEFT_CURLY_BRAC_SYMBOL}   {
                return LEFT_CURLY_BRAC_SYMBOL;
                                }
{RIGHT_CURLY_BRAC_SYMBOL}  {
                return RIGHT_CURLY_BRAC_SYMBOL;
                                }

{LEFT_COMMENT}  {
                return LEFT_COMMENT;
                                }

{RIGHT_COMMENT}  {
                return RIGHT_COMMENT;
                                }
 {WHITESPACE}   {

                                }

{ERROR}          {

                                }              
%%

main( argc, argv )
int argc;
char **argv;
    {
    ++argv, --argc;  /* skip over program name */
    if ( argc > 0 )
            yyin = fopen( argv[0], "r" );
    else
            yyin = stdin;

    yylex();
    }


int yywrap(void){return 1;}
/*用于C语言的令牌扫描程序*/
%{
#包括
#包括
#包括“parser.tab.h”
外部的YYSTYPE yylval;
%}
数字[0-9]
字母[a-zA-Z]
NUM{digit}+
ID{字母}+
关键词else | if | int | return | void | while
加号运算符“+”
减_运算符“-”
多重运算符“*”
DIV_运算符“/”
小于运算符“=”
相等运算符“=”
OBJ_相等运算符“=”
不等于运算符“!=”
逗号符号“,”
分号“
左括号符号“(”
右侧(BRAC-SYMBOL)
左方括号符号“[”
右方括号符号“]”
左卷曲括号符号“{”
右\u卷曲\u BRAC\u符号“}”
左注释“/*”
右注释“*/”
ELSE“ELSE”
如果“如果”
INT“INT”
返回“返回”
无效“无效”
WHILE“WHILE”
符号“+”|“-“|”*“|”/“|”=“|”=“|”!=“|”=“|”=“|”;“|”;“(“|”)“{”|“}”[“|”]“|”/*/”
空白[\t\n]+
注释“/*”(.)*({WHITESPACE})*(.)*“*/”
ERROR1{NUM}(({ID}{keyword}){NUM})+
ERROR2{ID}(({NUM}{keyword}){ID})+
ERROR3{KEY_WORD}(({ID}{NUM}){KEY_WORD})+
错误1 |错误2 |错误3
%%
{NUM}{
返回NUM;
}
{ELSE}{
返回其他;
}
{IF}{
如有需要,请返回;
}
{INT}{
返回INT;
}
{RETURN}{
回归;
}
{VOID}{
退货无效;
}
{WHILE}{
中途返回;
}
{ID}{
返回ID;
}
{PLUS_运算符}{
返回加号运算符;
}
{减_算子}{
返回-u运算符;
}
{MUL_算子}{
返回MUL_运算符;
}
{DIV_运算符}{
返回DIV_运算符;
}
{LESS_THAN_操作符}{
返回小于\u的\u运算符;
}
{LESS_THAN_或_EQUAL_OPER}{
返回小于或等于的操作;
}
{大于运算符}{
返回大于_的运算符;
}
{大于或等于运算符}{
返回大于或等于运算符;
}
{EQUAL_算子}{
返回等分算子;
}
{OBJ_等价算子}{
返回不等于运算符;
}
{NOT_EQUAL_操作符}{
返回不等于运算符;
}
{逗号\符号}{
返回逗号符号;
}
{分号\符号}{
返回分号符号;
}
{左括号符号}{
返回左括号符号;
}
{RIGHT_BRAC-SYMBOL}{
返回右括号符号;
}
{左方(左方)符号}{
返回左方括号符号;
}
{右(方)方(方)方(方)方(方)符号){
返回右方括号符号;
}
{左_卷曲_BRAC_符号}{
返回左_卷曲_BRAC_符号;
}
{右{卷曲}{
返回右\u卷曲\u布拉克\u符号;
}
{左注释}{
返回左注释;
}
{右注释}{
返回右注释;
}
{空白}{
}
{错误}{
}              
%%
主(argc、argv)
int-argc;
字符**argv;
{
++argv,--argc;/*跳过程序名*/
如果(argc>0)
yyin=fopen(argv[0],“r”);
其他的
yyin=stdin;
yylex();
}
int yywrap(void){return 1;}
解析器:

%{
#include <stdio.h>
#include <ctype.h>
#define YYDEBUG 1

%}

%token ID NUM PLUS_OPERATOR MINUS_OPERATOR MUL_OPERATOR DIV_OPERATOR LESS_THAN_OPERATOR LESS_THAN_OR_EQUAL_OPER GREATER_THAN_OPERATOR GREATER_THAN_OR_EQUAL_OPERATOR EQUAL_OPERATOR OBJ_EQUAL_OPERATOR           NOT_EQUAL_OPERATOR COMMA_SYMBOL SEMI_COLON_SYMBOL LEFT_BRAC_SYMBOL RIGHT_BRAC_SYMBOL LEFT_SQUARE_BRAC_SYMBOL RIGHT_SQUARE_BRAC_SYMBOL LEFT_CURLY_BRAC_SYMBOL RIGHT_CURLY_BRAC_SYMBOL           LEFT_COMMENT RIGHT_COMMENT ELSE IF INT RETURN VOID WHILE 

%expect 1


%%


program: declaration_list
;

declaration_list: declaration_list declaration
    | declaration                   { printf("njuwandusanduansduasdsdsdsa"); }
;

declaration : var_declaration 
    | fun_declaration               { printf("njuwandusanduansduasdsdsdsa");}
;

var_declaration : type_specifier ID SEMI_COLON_SYMBOL
    | type_specifier ID LEFT_SQUARE_BRAC_SYMBOL NUM RIGHT_SQUARE_BRAC_SYMBOL COMMA_SYMBOL       { printf("njuwandusanduansduasdsdsdsa"); }
;

type_specifier : INT
    | VOID                  { printf("njuwandusanduansduasdsdsdsa");}
;

fun_declaration : type_specifier ID LEFT_BRAC_SYMBOL params RIGHT_BRAC_SYMBOL compound_stmt
;

params :  param_list 
    | VOID
;

param_list : param_list COMMA_SYMBOL param
    | param
;

param : type_specifier ID 
    | type_specifier ID LEFT_SQUARE_BRAC_SYMBOL RIGHT_SQUARE_BRAC_SYMBOL
;
compound_stmt : LEFT_CURLY_BRAC_SYMBOL local_declarations statement_list RIGHT_CURLY_BRAC_SYMBOL
;

local_declarations : local_declarations var_declaration
    | /* empty */
;

statement_list : statement_list statement
    |/* empty */
;

statement : expression_stmt
    | compound_stmt
    | selection_stmt
    | iteration_stmt
    | return_stmt
;

expression_stmt : expression SEMI_COLON_SYMBOL
    | SEMI_COLON_SYMBOL
;

selection_stmt : IF LEFT_BRAC_SYMBOL  expression RIGHT_BRAC_SYMBOL  statement
    | IF LEFT_BRAC_SYMBOL  expression RIGHT_BRAC_SYMBOL statement ELSE statement
;

iteration_stmt : WHILE LEFT_BRAC_SYMBOL  expression RIGHT_BRAC_SYMBOL  statement
;

return_stmt : RETURN SEMI_COLON_SYMBOL
    | RETURN expression SEMI_COLON_SYMBOL
;

expression:  var EQUAL_OPERATOR expression 
    | simple_expression
;

var : ID
     | ID LEFT_SQUARE_BRAC_SYMBOL expression RIGHT_SQUARE_BRAC_SYMBOL
;

simple_expression : additive_expression relop additive_expression
    | additive_expression
;

relop : LESS_THAN_OR_EQUAL_OPER
    | LESS_THAN_OPERATOR
    | GREATER_THAN_OPERATOR
    | GREATER_THAN_OR_EQUAL_OPERATOR
    | OBJ_EQUAL_OPERATOR 
    | NOT_EQUAL_OPERATOR
;

additive_expression : additive_expression addop term
        | term          
;

addop : PLUS_OPERATOR
    | MINUS_OPERATOR    { printf("njuwandusanduansduasdsdsdsa"); }
;

term : term mulop factor     { $$ = $1 + $3; }
    | factor
;

mulop : MUL_OPERATOR
    | DIV_OPERATOR
;

factor : LEFT_BRAC_SYMBOL  expression RIGHT_BRAC_SYMBOL 
    | var
    | call
    | NUM
;

call : ID LEFT_BRAC_SYMBOL  args RIGHT_BRAC_SYMBOL 
;

args : arg_list
    |/* empty */
;

arg_list : arg_list COMMA_SYMBOL expression
    | expression

;



%%

main()
{

extern int yydebug;
yydebug=1;
return yyparse();
}


int yyerror(char * s)
{
fprintf(stderr, "%s\n",s);
return 0;
}
%{
#包括
#包括
#定义调试1
%}
%token ID NUM PLUS_操作符减_操作符MUL_操作符DIV_操作符小于_操作符小于_或_EQUAL_操作符大于_或_EQUAL_操作符EQUAL_操作符OBJ_EQUAL_操作符NOT_EQUAL_操作符逗号符号分号左括号符号右括号符号左方框符号右方框符号右方框符号LEFT_CURLY_BRAC_SYMBOL RIGHT_CURLY_BRAC_SYMBOL LEFT_COMMENT RIGHT_COMMENT ELSE IF INT返回VOID WHILE
%期望1
%%
节目:申报表
;
声明列表:声明列表声明
|声明{printf(“njuwandusanduasdsdsdsa”);}
;
声明:var_声明
|乐趣宣言{printf(“njuwandusanduasdsdsdsa”);}
;
变量声明:类型说明符ID分号符号
|类型_说明符ID LEFT_SQUARE_BRAC_SYMBOL NUM RIGHT_SQUARE_BRAC_SYMBOL COMMA_SYMBOL{printf(“njuwandusanduasdsdsdsa”);}
;
类型_说明符:INT
|VOID{printf(“njuwandus
flex flex.l
bison -d parser.y
gcc main.c parser.tab.c lex.yy.c -o myEXE
flex flex.l
gcc -c lex.yy.c -o lex.o
bison -d parser.y
gcc -c parser.tab.c -o parser.o
gcc -c main.c -o main.o
gcc main.o parser.o lex.o