java - 使用ANTLR4获取方法的注释

标签 java antlr antlr4

我正在编写一个简短的程序,它扫描 Java 源文件并使用 ANTLR4 查找其中的所有方法。对于每个方法,我想检查它是否是测试方法,并且我想通过检查该方法是否具有 @Test 注释来做到这一点。

如何获取我正在访问的每个方法的注释列表?这是到目前为止我的源代码:

public static void main(String... args) throws IOException {
    lexer = new JavaLexer(new ANTLRFileStream(sourceFile, "UTF-8"));
    parser = new JavaParser(new CommonTokenStream(lexer));
    ParseTree tree = parser.compilationUnit();

    ParseTreeWalker walker = new ParseTreeWalker();
    MyListener listener = new MyListener(printToFile);
    walker.walk(listener, tree);
}

public static class MyListener extends JavaBaseListener {
    @Override
    public void enterMethodDeclaration(JavaParser.MethodDeclarationContext ctx) {
        // Mark the method's boundaries and extract the method text
        int begin_offset = ctx.start.getStartIndex();
        int end_offset = ctx.stop.getStopIndex();
        Interval interval = new Interval(begin_offset, end_offset);
        String methodText = ctx.start.getInputStream().getText(interval);

        // Get the list of annotations - how?
    }

}

最佳答案

我将使用this Java grammar for antlr 。我正在研究内存,因为没有工具来测试我手头正在做的事情。阅读语法您可以快速了解到:

  • 注释与规则注释相对应(哇),因此您可以在生成的树的 AnnotationContext 中找到它们。
  • 注释链接到 classBodyDeclaration 规则中的类成员(例如方法)(修饰符可以是 classOrInterfaceModifier,也可以是注释)

在这种情况下,如果我们只有 MethodDeclarationContext,我们就无法获取注释。我们需要访问整棵树来找到对应的ClassBodyDeclarationContext。

现在我对听众并不熟悉。据我了解(而且不是很多),如果您需要在解析时工作,您应该使用它们。我宁愿只访问解析器生成的树。 ANTLR 应该为您创建一个名为 <your grammar name>ParserBaseVisitor 的访问者。您所要做的就是扩展此类并重写感兴趣节点的访问方法。

  • 访问 ClassBodyDeclarationContext。为此,您必须覆盖 visitClassBodyDeclaration(ClassBodyDeclarationContext ctx) .
  • 检查它是否是 ctx.memberDeclaration().methodDeclaration() 的方法。如果不是方法声明,则应为 null。否则它应该是一个 MethodDeclarationContext。
  • 如果不是,您可能需要访问子节点(如果它是类声明)。如果您扩展由antlr生成的ParserBaseVisitor,请调用super,因为它正是它的作用。
  • 如果它是一个方法,检索注释列表并用它做任何你想做的事情:-)

您应该能够像这样检索注释:

Set<AnnotationContext> annotations = new HashSet<AnnotationContext>();
for(ClassOrInterfaceModifier modifier: ctx.modifier()) {
    if (modifier.classOrInterfaceModifier().annotation()) {
        annotations.add(modifier.classOrInterfaceModifier().annotation());
    }
}

关于java - 使用ANTLR4获取方法的注释,我们在Stack Overflow上找到一个类似的问题: https://stackoverflow.com/questions/32089350/

相关文章:

java - 如何循环并为文件中的每个单词生成哈希键

python - ANTLR4 和 Python 目标

antlr - "skip"更改解析器行为

java - Antlr4 在自己的 Maven 模块中

java - antlr4 类似的标记定义

java - 有没有一个规范的例子说明如何使用 Antlr 4 来解析 SQL 语句?

java - 运行最大可用 "maximum heap size"的 java 应用程序

java - 使用二叉树,我想按连续顺序添加下一个节点,但是我的算法不太有效

java - 如何迭代 ANTLR 中的产生式

antlr - EBNF 语法(ANTLR)