Синтаксическая ошибка в бизоне, но я не вижу свою ошибку - PullRequest
0 голосов
/ 27 ноября 2018

Я написал простую программу, которая, надеюсь, является инфиксным калькулятором, который выводит постфиксное представление и его значение.Я не знаю почему, но когда я запускаю его и передаю ему простые данные, я получаю синтаксическую ошибку.Вот что я передаю, что я получаю вместе с файлами src.

Исполнение:

2+2+2
2 2 + 
4
syntax error

Файл Bison:

%{
#include <stdio.h>
#include <stdlib.h>
#include <math.h>

extern int yylex();
extern int yyparse();

void yyerror(const char *msg);
%}

%union {
    int ival;
}

%token <ival> NUM
%type <ival> N M P A

%%

S : A               {printf("\n%d\n", $1);}
    ;

A   : P '-' P       {printf("- "); $$ = (int)($1 - $3);}
    | P '+' P       {printf("+ "); $$ = (int)($1 + $3);}
    | P             {$$ = $1;}
    ;

P   : M '/' M       {printf("/ "); $$ = (int)($1 / $3);}
    | M '*' M       {printf("* "); $$ = (int)($1 * $3);}
    | M '%' M       {printf("% "); $$ = (int)($1 % $3);}
    | M             {$$ = $1;}
    ;

M   : N '^' N       {printf("^ "); $$ = (int)pow($1, $3);}
    | N             {$$ = $1;}
    ;

N   : '(' A ')'     {$$ = $2;}
    | '-' N         {printf("-%d ", $2); (int)($$ = -$2);}
    | NUM           {printf("%d ", $1); (int)($$ = $1);}
    ;

%%

void main() {
    yyparse();
    return;
}

void yyerror(const char *msg) {
    fprintf(stderr, "%s\n", msg);
}

Файл Flex:

%{
#include <stdio.h>
#include <stdlib.h>
#include "bison.tab.h"
%}

%%

#.*\n
"\\"\n
[0-9]+      {
                yylval.ival = atoi(yytext); 
                return NUM;
            }

[-+*/^%()]  {
                return yytext[0];
            }
[ \t\n]

%%

Вы видите мою ошибку?Мэйби, я просто недостаточно хорошо читал документацию Бизона.На нем довольно сложно найти какие-либо учебные пособия.

1 Ответ

0 голосов
/ 27 ноября 2018

Хорошо, я нашел решение, но я не знаю, почему это сработало. Если кто-то захочет уточнить, я был бы признателен за то, что я не очень хорошо разбираюсь в официальных языках.Я изменил:

P   : M '/' M       {printf("/ "); $$ = (int)($1 / $3);}
    | M '*' M       {printf("* "); $$ = (int)($1 * $3);}
    | M '%' M       {printf("% "); $$ = (int)($1 % $3);}
    | M             {$$ = $1;}
    ;

Изменен на:

P   : P '/' M       {printf("/ "); $$ = (int)($1 / $3);}
    | P '*' M       {printf("* "); $$ = (int)($1 * $3);}
    | P '%' M       {printf("% "); $$ = (int)($1 % $3);}
    | M             {$$ = $1;}
    ;

И сделал соответственно каждому нетерминалу.

...