我使用ANTLR v4 Java语法(可用here)来解析Java代码。其中一个产品看起来像这样:
expression
: primary
| expression '.' Identifier
| expression '.' 'this'
| expression '.' 'new' nonWildcardTypeArguments? innerCreator
| expression '.' 'super' superSuffix
| expression '.' explicitGenericInvocation
| expression '[' expression ']'
| expression arguments
| // Lots of other patterns...
;
expression '.' Identifier
匹配简单的成员访问权限,expression arguments
匹配方法调用。您可以查看此作品的完整来源here。
出于语法高亮的目的,我想引入额外的冗余模式来检测我称之为命名方法调用的内容。 bar()
或foo.bar()
将被视为命名方法调用,bar
是方法的名称。对于这样的表达式,我希望bar
颜色为绿色,即使标识符通常为白色。但是,在foo.bar
或foo.bar[0]()
中,任何内容都不应为绿色。前者bar
没有调用方法,后者bar[0]
不是有效的标识符。
我在expression arguments
之前添加了这两个额外的模式(注意:arguments
与原始源代码中的'(' expressionList? ')'
同义):
expression
: // ...
| expression '[' expression ']'
| Identifier arguments namedMethodInvocationStub // Detect bar()
| expression '.' Identifier arguments namedMethodInvocationStub // Detect (some().complicated().expression()).bar()
| expression arguments
| // ...
;
namedMethodInvocationStub
:
;
(此处,namedMethodInvocationStub
是我添加的额外虚拟制作。我的想法是我可以覆盖VisitExpression
并检查最后一个孩子是否为namedMethodInvocationStub
。如果是,然后我们匹配一个命名的方法调用,所以遍历所有Identifier
类型的直接子项并将它们涂成绿色。无论如何,这只是为了揭开它的神秘面纱,它没有直接相关我的问题如下。)
我希望此规则更改为foo.bar()
,之前已解析为(expression '.' Identifier) arguments
,现在解析为expression '.' Identifier arguments namedMethodInvocationStub
。但是,它仍然以与以前相同的方式解析,无论我是否删除namedMethodInvocationStub
。这是为什么?
答案 0 :(得分:0)
我相信你不能在ANTLR(或任何其他词法分析器)中匹配空规则/令牌(namedMethodInvocationStub)
ANTLR: empty condition not working
What is the equivalent for epsilon in ANTLR BNF grammar notation?
您是否在ANTLR代码生成阶段看到任何错误/警告?