ANTLR4 词法分析器规则不匹配正确的文本块

ANTLR4 lexer rules not matching correct block of text

我试图了解 ANTLR4 如何基于词法分析器和解析器规则工作,但我在以下示例中遗漏了一些内容:

我正在尝试解析文件并匹配所有数学加法(例如 1+2+3 等)。我的文件包含以下文本:

start
4 + 5 + 22 + 1
other text other text test test
test test other text
55 other text
another text 2 + 4 + 255
number 44
end

我想匹配

4 + 5 + 22 + 1

2 + 4 + 255

我的语法如下:

grammar Hello;
hi : expr+ EOF;
expr : NUM (PLUS NUM)+;

PLUS : '+' ;
NUM : [0-9]+ ;
SPACE : [\n\r\t ]+ ->skip;
OTHER : [a-z]+ ;

我的抽象语法树可视化为

为什么规则 'expr' 匹配文本 'start'?我还收到错误消息“无关输入 'start' 期望 NUM

如果我对我的语法进行以下更改

OTHER : [a-z]+ ->skip;

错误消失了。除了上图中的文字 '55 其他文字 another text' 将表达式匹配为 AST 中的节点。为什么会这样?

以上所有内容都与词法分析器匹配输入的方式有关吗?我知道词法分析器寻找第一个最长的匹配规则,但我如何更改我的语法以便只匹配添加的内容?

Why does rule 'expr' matches the text 'start'?

没有。当标记在树中显示为红色时,表示出现错误。该标记与任何可能的替代项都不匹配,因此产生了一个错误,解析器继续使用下一个标记。

In addition in the image above text '55 other text another text' matches the expression as a node in the AST. Why is this happening?

跳过 OTHER 个标记后,您的输入基本上如下所示:

4 + 5 + 22 + 1 55 2 + 4 + 255 44

4 + 5 + 22 + 1可以解析为表达式,没问题。之后,解析器需要一个 + (继续表达式)或一个数字(开始一个新表达式)。所以当它看到 55 时,表示新表达式的开始。现在它需要 +(因为语法规定 PLUS NUM 必须在表达式中的第一个数字之后至少出现一次)。它实际得到的是数字2。因此它会产生错误并忽略该标记。然后它看到 +,这是它所期望的。然后它继续这种方式直到 44,它再次开始一个新的表达式。因为后面没有 +,这是另一个错误。

All the above have to do with the way lexer matches an input?

不是真的。 "start 4 + 5" 的标记序列是 OTHER NUM PLUS NUM,如果您跳过 OTHER,则只是 NUM PLUS NUM。 “55 skippedtext 2 + 4”的标记序列是 NUM NUM PLUS NUM。我想这正是您所期望的。

相反,似乎让您感到困惑的是 ANTLR 如何从错误中恢复(或者 它是如何从错误中恢复的)。