这两天继续学习Flex/Bison,不学好这个,没法完成作业了。
Flex/Bison很好玩,几十行代码,规定了TOKEN的正则表达式和语法推理的规则,就能做一个简单的语言解释器,的例如我做了个计算器解释器的练习,源代码:
fb1-4.l
/* rocognize tokens for the calculator */
%{
#include "fb1-5.tab.h"
%}
%%
"+" {return ADD; }
"-" {return SUB; }
"*" {return MUL; }
"/" {return DIV; }
"|" {return ABS; }
"(" {return OP; }
")" {return CP; }
"//".* /* ignore comments */
[0-9]+ { yylval = atoi(yytext); return NUMBER; }
n {return EOL; }
[ t] { /* ignore whitespace */ }
. { printf("Mystery character %c\n", *yytext); }
%%
fb1-5.y:
/* simplest version of calculator */
%{
#include <stdio.h>
%}
/* declare tokens */
%token NUMBER
%token OP CP
%token ADD SUB MUL DIV ABS
%token EOL
%%
calclist: /* nothing */
| calclist exp EOL {printf(" = %d\n",$2);}
;
exp: factor /* default $$=$1 */
| exp ADD factor { $$ = $1 + $3; }
| exp SUB factor { $$ = $1 - $3; }
;
factor: term /*default $$ = $1 */
| factor MUL term { $$ = $1 * $3; }
| factor DIV term { $$ = $1 / $3; }
;
term: NUMBER /* default $$ = $1 */
| ABS term { $$ = $2 >= 0 ? $2 : -$2;}
| OP exp CP { $$ = $2; } //New rule
;
%%
int main(int argc, char **argv)
{
yyparse();
return 0;
}
int yyerror(char *s)
{
fprintf(stderr, "error: %s\n", s);
return 0;
}
int yywrap(void)
{
return 1;
}
生成解释器源代码用的命令行:
flex fb1-4.l
bison -d fb1-5.y
此时会生成lex.yy.c, fb1-5.h, fb1-5.c几个源代码,然后编译(我用的是WINXP的32位环境,所以编译时加参数-m32)
gcc -m32 fb1-5.tab.c lex.yy.c -o calc.exe
此处生成的calc.exe就是个计算器了。运行后结果:
C:flexbison>calc
4+3*(5-2)
= 13
5+3*4
= 17