2017-06-13 64 views
0

我正在使用ANTLR v4 Java语法(可用here)解析Java代码。其中生产的是这样的:为什么这些模式在这个ANTLR生产中不匹配?

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.barfoo.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

我相信你无法比拟的空规则/令牌(namedMethodInvocationStub)在ANTLR(或任何其他词法分析器)

ANTLR: empty condition not working

What is the equivalent for epsilon in ANTLR BNF grammar notation?

你看到任何错误ANTLR代码中/警告生成阶段?

+0

不过,它似乎在发生或者没有'namedMethodInvocationStub'。 –

+0

我没有在您提供的位置找到模式“表达参数”https://github.com/antlr/grammars-v4/blob/master/java/Java.g4#L497-L538 –

+0

对不起,我调整了代码有点让它更整洁。 'arguments'是另一个非终结符([here](https://github.com/antlr/grammars-v4/blob/master/java/Java.g4#L604-L606))与''('expressionList?'同义) “'。 –

相关问题