ANTLR4:如何在同一标签的规则中设置不同的上下文?

ANTLR4: How to set different context within rule for the same tag?

我有这样的语法:

grammar SearchQuery;

queryDeclaration                        : predicateGroupItem predicateGroupItemWithBooleanOperator* ;
predicateGroupItemWithBooleanOperator   : groupOperator predicateGroupItem ;
predicateGroupItem                      : LEFT_BRACKET variable variableDelimiter
                                                expression expressionWithBoolean* RIGHT_BRACKET ;

variable                                : VARIABLE_STRING ;
variableDelimiter                       : VAR_DELIMITER  ;

expressionWithBoolean                   : boolOperator expression ;

expression                              : value ;

value                                   : polygonType;

boolOperator                            : or
                                        ;

or                                      : OR ;

groupOperator                           : AND ;

polygonType                             : POLYGON LEFT_BRACKET pointList (POLYGON_DELIMITER pointList)* RIGHT_BRACKET ;
longType                                : LONG ;
doubleType                              : DOUBLE ;

pointList                               : point
                                        | LEFT_BRACKET point ( POLYGON_DELIMITER point)* RIGHT_BRACKET
                                        ;

point                                   : latitude longitude ;

latitude                                : longType
                                        | doubleType
                                        ;

longitude                               : longType
                                        | doubleType
                                        ;

POLYGON                                 : [pP] [oO] [lL] [yY] [gG] [oO] [nN] ;


LONG                                    : DIGIT+ ;

DOUBLE                                  : DIGIT+ '.' DIGIT*
                                        | '.' DIGIT+
                                        ;

AND                                     : [aA] [nN] [dD] ;
OR                                      : COMMA
                                        | [oO] [rR]
                                        ;

VARIABLE_STRING                         : [a-zA-Z0-9.]+ ;
COMMA                                   : ',' ;
POLYGON_DELIMITER                       : ';' ;
VAR_DELIMITER                           : ':' ;

RIGHT_BRACKET                           : ')' ;
LEFT_BRACKET                            : '(' ;

WS                                      : [ \t\r\n]+ -> skip ;

fragment DIGIT                          : [0-9] ;

问题是我不能在polygonTypepointList规则中同时使用不同规则的COMMA标签(我需要使用COMMA除了 POLYGON_DELIMITER) 和 boolOperator 规则(使用了 COMMA) 换句话说,如果我们将 POLYGON_DELIMITER 更改为 COMMA 并且 用这样的值测试这样的语法

(polygons: polygon(20 30.4, 23.4 23),
           polygon(20 30.4, 23.4 23),
           polygon(20 30.4, 23.4 23))

我们会得到一个错误

mismatch input: ',' expecting {',', ')'}

如果有人能帮助我理解这个问题,我会很高兴。

P.S。如果我们不更改当前语法,则测试的值为

(poligons: polygon(20 30.4; 23.4 23),
           polygon(20 30.4; 23.4 23),
           polygon(20 30.4; 23.4 23))

由于这些规则:

OR                                      : COMMA
                                        | [oO] [rR]
                                        ;

COMMA                                   : ',' ;

词法分析器永远不会生成 COMMA 标记,因为它已经与 OR 标记匹配。并且因为 ORCOMMA 之前定义,它获得优先权。

这就是错误消息 mismatch input: ',' expecting {',', ')'} 的真正含义。换句话说:mismatch input: OR expecting {COMMA, RIGHT_BRACKET}

您应该做的(如果 OR 运算符可以是 "or" 或“,”)让解析器规则 or 匹配 COMMA:

or                                      : OR
                                        | COMMA
                                        ;

OR                                      : [oO] [rR]
                                        ;

COMMA                                   : ',' ;