Antlr4 使用二进制运算符分析不匹配的输入

Antlr4 使用二进制运算符分析不匹配的输入,antlr4,Antlr4,我正在尝试解析ANTLR中的现有语言,该语言目前正在使用Ruby库Parslet进行解析 这是我语法的精简版本: grammar FilterMin; filter : condition_set; condition_set: condition_set_type (property_condition)?; condition_set_type: '=' | '^='; property_condition: property_lhs CONDITION_SEPARATOR propert

我正在尝试解析ANTLR中的现有语言,该语言目前正在使用Ruby库Parslet进行解析

这是我语法的精简版本:

grammar FilterMin;

filter : condition_set;
condition_set: condition_set_type (property_condition)?;
condition_set_type: '=' | '^=';
property_condition: property_lhs CONDITION_SEPARATOR property_rhs;
property_lhs: QUOTED_STRING;
property_rhs: entity_rhs | contains_rhs;
contains_rhs: CONTAINS_OP '(' contains_value ')';
contains_value: QUOTED_STRING;
entity_rhs: NOT_OP? MATCH_OP? QUOTED_STRING;

// operators

MATCH_OP: '~';
NOT_OP: '^';
CONTAINS_OP: 'contains';
QUOTED_STRING: QUOTE STRING QUOTE;
STRING: (~['\\])*;
QUOTE: '\'';
CONDITION_SEPARATOR: ':';
此解析无法同时解析
='foo':'bar'
='foo':contains('bar')
,使用相同的:
不匹配的输入:'expecting':'
不匹配的输入:'contains('expecting':'


为什么这些输入没有被解析?

您的
字符串
规则匹配所有不是反斜杠或单引号的内容。因此它与除
QUOTED\u STRING
之外的所有其他词法规则重叠。由于lexer总是选择产生最长匹配的规则,并且几乎总是
字符串
,因此您的lexer将产生一组
字符串
令牌,而不会产生任何
条件分隔符
令牌


由于您从未在解析器规则中使用
STRING
,因此它不需要是实际类型的令牌。事实上,您从未希望生成
STRING
令牌,您只希望它作为
QUOTED\u STRING
令牌的一部分进行匹配。因此它应该是
片段

,并且字符串可以匹配空string、 这也不好。很容易忘记这一事实并假设某个东西被消费了,以后在某个地方使用这样的规则时。最好在调用者中标记一个可选的规则。