从Java文件获取Java类名

时间:2014-04-15 12:02:02

标签: java

我需要有关每个java类所在位置的信息。 java文件中可以有多个类。因此,获取java文件名是不正确的方法......我可以提出的一种可能的方法是使用Eclipse AST库。但我想知道有一种更简单的方法,因为我不熟悉Eclipse AST ...如果我应该使用Eclipse AST,请给我一些代码片段,帮助我搜索相关信息。

更新

输入:java项目的位置

输出:java文件和java文件中声明的java类之间的映射信息。

e.g。

在A.java中,

public class A {
    System.out.println("A class");
    class InnerA{
        System.out.println("A inner class");
    }
}

class B {
    System.out.println("B class");
}

A.java文件链接到A.class,A $ InnerA.class和B.class

2 个答案:

答案 0 :(得分:1)

我将假设您知道如何查找项目目录中的所有.java文件。使用javaparser,您可以列出每个文件中声明的类型,如下所示:

public class ParserTest {

  public static void main(String[] args) throws Exception {
    CompilationUnit cu;

    try (FileInputStream in = new FileInputStream("C:\\tmp\\Test.java")) {
      cu = JavaParser.parse(in);
    }

    List<TypeDeclaration> types = cu.getTypes();
    ArrayList<String> parents = new ArrayList<>();

    for (TypeDeclaration typeDeclaration : types) {
      printTypes(typeDeclaration, parents);
    }
  }

  private static void printTypes(BodyDeclaration item, List<String> parents) {
    if (item instanceof TypeDeclaration) {

      TypeDeclaration type = (TypeDeclaration) item;

      System.out.println(getClassName(type.getName(), parents));
      List<BodyDeclaration> members = type.getMembers();

      List<String> cloneOfParents = new ArrayList<>(parents);
      cloneOfParents.add(type.getName());

      for (BodyDeclaration bodyDeclaration : members) {
        printTypes(bodyDeclaration, cloneOfParents);
      }
    }
  }

  private static String getClassName(String name, List<String> parents) {
    StringBuilder builder = new StringBuilder();
    for (String string : parents) {
      builder.append(string);
      builder.append(".");
    }

    return builder.append(name).toString();
  }
}

在我的示例中,Test.java包含:

public class Test {

  class InnerClass {
  }

}

class Foo {}

并打印代码:

Test
Test.InnerClass
Foo

答案 1 :(得分:0)

我没有注意到@Duncan的回答..我使用了JDT AST解析器。我看过这篇文章, http://www.programcreek.com/2011/11/use-jdt-astparser-to-parse-java-file/,我可以按如下方式编写代码。

//use ASTParse to parse string
public static void parse(String str) {
    ASTParser parser = ASTParser.newParser(AST.JLS3);
    parser.setSource(str.toCharArray());
    parser.setKind(ASTParser.K_COMPILATION_UNIT);

    final CompilationUnit cu = (CompilationUnit) parser.createAST(null);
    cu.accept(new ASTVisitor() {
        String packageName="";

        public boolean visit(TypeDeclaration node) {
            String className=node.getName().getFullyQualifiedName();
            if (packageName!="")
                System.out.println(packageName+"."+className);
            else
                System.out.println(className);

            return false;
        }

        public boolean visit(PackageDeclaration node) {
            packageName=node.getName().getFullyQualifiedName();
            return false;
        }
    });

}

这不是我想要的,因为这段代码不会打印内部类。但是,通过在类目录中搜索类,我可以得到内部类,其名称以打印的类名开头。

谢谢你,@ Duncan。我读了你的代码并运行了代码。它就像魅力一样。我注意到代码中的一些语法是Java 7语法。我还不熟悉它。但是我从你的代码中学到了它。 :)