【问题标题】:How to determine the class is AnnotationDeclaration or TypeDeclaration using JDT如何使用JDT判断类是AnnotationDeclaration还是TypeDeclaration
【发布时间】:2014-03-25 21:42:34
【问题描述】:

我正在使用 JDT ASTParser 来解析给定文件夹中的所有 Java 文件。我写了以下代码:

private void parse(String fileContent) {
    // TODO Auto-generated method stub
    //advise the parser to parse the code following to the Java Language Specification, Third Edition.
    ASTParser parser = ASTParser.newParser(AST.JLS3); 
    // tell the parser, that it has to expect an ICompilationUnit (a pointer to a Java file) as input.
    parser.setKind(ASTParser.K_COMPILATION_UNIT);       
    parser.setSource(fileContent.toCharArray());
    parser.setResolveBindings(true);
    final CompilationUnit cu = (CompilationUnit) parser.createAST(null);

    cu.accept(new ASTVisitor() {
        public boolean visit(AnnotationTypeDeclaration node) {

            System.out.println("Annotaion: " + node.getName());

            return true;
        }

        public boolean visit(TypeDeclaration node) {

            System.out.println("Type: " + node.getName());

            return true;
        }
    });     

}

问题是,有两种 Java 类:

  • Bound2Processor.java 是一个普通的java类:TypeDeclaration

    package com.richardle;
    
    import ...;
    
    
    public class Bound2Processor extends AbstractAnnotationProcessor<Bound, CtMethod<?>> {
       ...
    }
    
  • Bound.java 为注解声明类:AnnotationTypeDeclaration

        package com.richardle;    
        public @interface Bound {
            double min(); 
        }
    

    但是在运行代码时,我得到了输出:

    File: D:\SOFTWARE\Android\SpoonTest\src\com\richardle\Bound.java // no thing print here
    File: D:\SOFTWARE\Android\SpoonTest\src\com\richardle\Bound2Processor.java
    Type: Bound2Processor
    

问题是注释类的名称没有打印出来。也许 ASTParser 没有调用函数public boolean visit(AnnotationTypeDeclaration node)。你能告诉我为什么 ASTParser 忽略这个函数吗?又如何判断一个类是普通类还是注解声明?

【问题讨论】:

    标签: java annotations eclipse-jdt


    【解决方案1】:

    只有在 Java 合规性设置为大于 1.5 时,ASTParser 才会解析注解。

    来自 ASTParser Javadoc:

    为了解析 1.5 的代码,一些编译器选项需要设置为 1.5

    所以你需要在你的代码中添加以下几行:

    Map options = JavaCore.getOptions();
    JavaCore.setComplianceOptions(JavaCore.VERSION_1_5, options);
    parser.setCompilerOptions(options);
    

    编辑

    这是我用于测试的完整 parse 方法:

    public static void parse(String fileContent) {
        //advise the parser to parse the code following to the Java Language Specification, Third Edition.
        ASTParser parser = ASTParser.newParser(AST.JLS3); 
        Map options = JavaCore.getOptions();
        JavaCore.setComplianceOptions(JavaCore.VERSION_1_5, options);
        parser.setCompilerOptions(options);
    
        // tell the parser, that it has to expect an ICompilationUnit (a pointer to a Java file) as input.
        parser.setKind(ASTParser.K_COMPILATION_UNIT);       
        parser.setSource(fileContent.toCharArray());
        parser.setResolveBindings(true);
        final CompilationUnit cu = (CompilationUnit) parser.createAST(null);
    
        cu.accept(new ASTVisitor() {
            public boolean visit(AnnotationTypeDeclaration node) {
                System.out.println("Annotaion: " + node.getName());
                return true;
            }
    
            public boolean visit(TypeDeclaration node) {
                System.out.println("Type: " + node.getName());
                return true;
            }
        });
    }
    

    这里是我提供给parse(String)的非常简单的类:

    public @interface Bound {
        double min(); 
    }
    
    public class Bound2Processor {
    
    }
    

    这是输出:

    Annotaion: Bound
    Type: Bound2Processor
    

    【讨论】:

    • 我按照你的建议做了。但是注释仍然没有被打印出来
    • 您确定您尝试解析的文件没有任何编译错误吗?在这种情况下,ASTParser 不会抛出异常,您可能会得到一个空的 CompilationUnit。请参阅 CompilationUnit#getProblems() 以获取解析期间产生的问题列表。
    • @Richard 我还在答案中添加了我的测试代码。添加 Java 合规性设置后,它与您的基本相同。
    • options.put(JavaCore.COMPILER_COMPLIANCE, JavaCore.VERSION_1_6); options.put(JavaCore.COMPILER_CODEGEN_TARGET_PLATFORM, JavaCore.VERSION_1_6); options.put(JavaCore.COMPILER_SOURCE, JavaCore.VERSION_1_6);有效!非常感谢
    猜你喜欢
    • 2015-07-06
    • 2020-10-18
    • 1970-01-01
    • 1970-01-01
    • 1970-01-01
    • 2016-09-16
    • 1970-01-01
    • 2011-10-28
    • 2011-09-12
    相关资源
    最近更新 更多