我正在尝试实现一种允许并列乘法的语法。这是用于解析 CAS 的多项式输入。
据我所知,它工作得很好,除了少数边缘情况。我发现了两个问题:
- 与其他规则冲突,例如,
a^2 b
被(错误地)解析为(^ a (* 2 b))
,而不是(* (^ a 2) b)
。 - yacc(bison) 报告
28 shift/reduce conflicts
和8 reduce/reduce conflicts
.
我很确定正确解决第一个问题也会解决第二个问题,但到目前为止我还没有成功。
以下是我正在使用的语法的要点:
%start prgm
%union {
double num;
char *var;
ASTNode *node;
}
%token <num> NUM
%token <var> VAR
%type <node> expr
%left '+' '-'
%left '*' '/'
%right '^'
%%
prgm: // nothing
| prgm '\n'
| prgm expr '\n'
;
expr: NUM
| VAR
| expr '+' expr
| expr '-' expr
| expr '*' expr
| expr '/' expr
| expr '^' expr
| expr expr %prec '*'
| '-' expr
| '(' expr ')'
;
%%
删除并列规则 ( expr expr %prec '*'
) 解决了 shift/reduce 和 reduce/reduce 警告。
请注意,ab
在我的语法中应该是(* a b)
. 多字符变量前面应该有一个引号('
);这已经在lex
文件中处理得很好。词法分析器完全忽略了空格(
)和制表符(\t
)。
我知道这个问题,但这里使用并列似乎并不表示乘法。
任何意见或帮助将不胜感激!
PS 如果有帮助,这是整个项目的链接。