So I'm making a really simple Flex and Bison program, to solve mathematical expressions, but for some reason the output is always 0. I have been following the book, 'Flex and Bison' by O'Reilly, my code is almost the same as in the book, but still doesn't work. Been at it for some time now, help will be appreciated.
Here's the .l file:
%{
#include "simple.tab.h"
/* enum yytokentype {
NUMBER = 258,
ADD,
SUB,
MUL,
DIV,
ABS,
EOL
};
int yylval; */
%}
%%
"+" { return ADD; }
"-" { return SUB; }
"*" { return MUL; }
"/" { return DIV; }
"|" { return ABS; }
[0-9]+ { yylval = atoi(yytext); return NUMBER; }
\n { return EOL; }
[ \t] { /* ignore whitespace */ }
. { printf("Mystery character %c\n", *yytext); }
%%
And the .y file:
%{
#include<cstdio>
int yylex();
int yyerror(const char *s);
%}
/* token declaration */
%token NUMBER
%token ADD SUB MUL DIV ABS
%token EOL
%%
calclist:
| calclist exp EOL { printf("= %d\n",$1); }
;
exp: factor
| exp ADD factor { $$=$1+$3; }
| exp SUB factor { $$=$1-$3; }
;
factor: term
| factor MUL term { $$=$1*$3; }
| factor DIV term { $$=$1/$3; }
;
term: NUMBER
| ABS term { $$=$2 >=0 ? $2 : -$2; }
;
%%
int main(int argc, char **argv)
{
yyparse();
}
int yyerror(const char *s)
{
fprintf(stderr,"error: %s\n",s);
}
Output:
$ bison -d simple.y
$ flex stuff.l
$ g++ simple.tab.c lex.yy.c -lfl -o simple
$ ./simple
1+2
= 0
1*2
= 0
1/1
= 0
4/2
= 0
25/5
= 0
|1
= 0
Also, if someone can suggest a better and simpler book, it'd be appreciated.
In this statement, $1
is the value of calclist
:
| calclist exp EOL { printf("= %d\n",$1); }
What you want is the value of exp
:
| calclist exp EOL { printf("= %d\n",$2); }