我写了一个简单的语法来识别一些表达式。 在这里,我发布了一个更简单的版本,我写它只是为了简化我的解释。这个更简单的版本可以识别如下表达式:
- 这是一段文字
- [n]这是另一篇文章[/n]
- [n][n]这是一个化合物 表达式[/n][/n]
我的问题是当我提交如下表达式时: [i]这应该只生成一个识别异常[/n]
抛出识别异常,但解析器进入无限递归,因为它匹配'[',但当它不匹配'i'时它会丢失自己。我认为这是因为我的语法文本组件不能包含方括号。所以,我要发布语法。
grammar ErrorTest;
expression
: rawText EOF
| command EOF
;
rawText
: word+
;
word
: ESPACE* TEXT ESPACE*
;
command
: simpleCommand
| compoundCommand
;
simpleCommand
: HELP
;
compoundCommand
: rawText
| BEGIN compoundCommand END
;
HELP : '[help]';
BEGIN : '[n]';
END : '[/n]';
ESPACE : ' ';
TEXT : ~(' '|'['|']')*;
我该如何解决?
最佳答案
单词匹配空串因为在
word
: ESPACE* TEXT ESPACE*
;
TEXT 匹配导致的空字符串
rawText
: word+
;
无限循环
改变
TEXT : ~(' '|'['|']')*;
到
TEXT : ~(' '|'['|']')+;
这只会让你的语法变得模棱两可。
对此的思考方式是,rawText可以通过多种方式匹配空字符串
- 零个 TEXT token
- 一个长度为 0 的 TEXT token 。
- 两个长度为 0 的 TEXT 标记。
- 三个长度为 0 的 TEXT 标记。
- ...
当您遇到语法错误 ([i]
) 时,就会出现这种情况,因为它会尝试每一种替代方案,看看是否有任何替代方案可以解决错误。
要摆脱任何二次行为,你真的应该让它完全明确。
rawText : ign (word (ign word)*)? ign;
ign : ESPACE*;
word : TEXT;
原始修复的问题是 rawText 可以通过多种方式匹配 "foo"
:
TEXT("foo")
TEXT("fo"), ESPACE(""), TEXT("o")
TEXT("f"), ESPACE(""), TEXT("oo")
TEXT("f"), ESPACE(""), TEXT("o"), ESPACE(""), TEXT("o")
关于java - ANTLR语法中的无限递归,我们在Stack Overflow上找到一个类似的问题: https://stackoverflow.com/questions/10325205/