我正在为SQL的一个子集编写语法,我在下面粘贴了它:
grammar Sql;
sel_stmt : SEL QUANT? col_list FROM tab_list;
as_stmt : 'as' ID;
col_list : '*' | col_spec (',' col_spec | ',' col_group)*;
col_spec : (ID | ID '.' ID) as_stmt?;
col_group : ID '.' '*';
tab_list : (tab_spec | join_tab) (',' tab_spec | ',' join_tab)*;
tab_spec : (ID | sub_query) as_stmt?;
sub_query : '(' sel_stmt ')';
join_tab : tab_spec (join_type? 'join' tab_spec 'on' cond_list)+;
join_type : 'inner' | 'full' | 'left' | 'right';
cond_list : cond_term (BOOL_OP cond_term)*;
cond_term : col_spec (COMP_OP val | between | like);
val : INT | FLT | SQ_STR | DQ_STR;
between : ('not')? 'between' val 'and' val;
like : ('not')? 'like' (SQ_STR | DQ_STR);
WS : (' ' | '\t' | '\n')+ -> skip;
INT : ('0'..'9')+;
FLT : INT '.' INT;
SQ_STR : '\'' ~('\\'|'\'')* '\'';
DQ_STR : '"' ~('\\'|'"')* '"';
BOOL_OP : ',' | 'or' | 'and';
COMP_OP : '=' | '<>' | '<' | '>' | '<=' | '>=';
SEL : 'select' | 'SELECT';
QUANT: 'distinct' | 'DISTINCT' | 'all' | 'ALL';
FROM: 'from' | 'FROM';
ID : ('A'..'Z' | 'a'..'z')('A'..'Z' | 'a'..'z' | '0'..'9')*;
我正在测试的输入是select distinct test.col1 as col, test2.* from test join test2 on col='something', test2.col1=1.4
。输出解析树将test2的最后一次外观与a匹配,因此不知道如何处理输入的其余部分。最后一个'test2'标记之前的逗号成为节点的子节点,当它应该是子节点时。
我的问题是幕后发生了什么导致这种情况?
答案 0 :(得分:0)
显然,当您使用文字符号作为令牌并让它成为另一个令牌的一部分时,ANTLR不喜欢它。就我而言,逗号令牌既可以用作文字标记,也可以用作BOOL_OP标记的一部分。
未来的问题可能是当相同的符号被用作仅适用于特定范围的不同令牌的部分时,ANTLR如何消除歧义。但是,现在回答这个问题。