我是ANTLR的新手,并在ANTLRWorks1.4.3中尝试遵循语法。
command
: 'go' SPACE+ 'to' SPACE+ destination
;
destination
: (UPPER | LOWER) (UPPER | LOWER | DIGIT)*
;
SPACE
: ' '
;
UPPER
: 'A'..'Z'
;
LOWER
: 'a'..'z'
;
DIGIT
: '0'..'9'
;
这似乎工作正常,除非'目的地'包含关键字'go'和'to'的前两个字符。 例如,如果我给出以下命令:
go to Glasgo
节点树显示如下:
我期待它将填充词与目标匹配。
我甚至尝试更改关键字,例如'travel'而不是'go'。在这种情况下,如果目的地中有'tr',ANTLR会抱怨。
知道为什么会这样吗?以及如何解决这个问题?
提前致谢。
答案 0 :(得分:1)
ANTLR词法分析器和解析器是严格分开的。您的输入首先被标记化,然后解析器规则对所述标记进行操作。
在您的情况下,输入go to Glasgo
被标记为以下X标记:
'go'
' '
(SPACE)'to'
'G'
(UPPER)'l'
(LOWER)'a'
(LOWER)'s'
(LOWER)'go'
留下了“悬空”'go'
关键字。这就是ANTLR的词法分析器的工作原理:你无法改变它。
在您的情况下,一个可能的解决方案是使destination
成为词法分析器规则而不是解析器规则:
command
: 'go' 'to' DESTINATION
;
DESTINATION
: (UPPER | LOWER) (UPPER | LOWER | DIGIT)*
;
SPACE
: ' ' {skip();}
;
fragment UPPER
: 'A'..'Z'
;
fragment LOWER
: 'a'..'z'
;
fragment DIGIT
: '0'..'9'
;
导致:
如果您不完全确定两者之间的区别,请参阅:Practical difference between parser rules and lexer rules in ANTLR?
有关fragment
s的更多信息:What does "fragment" mean in ANTLR?
PS。 Glasgo的瓦特吗?