我该怎么做用番石榴获得给定包的所有类

时间:2015-02-04 17:13:47

标签: java reflection package guava

我正在开发一个maven项目,我在我的pom.xml文件中添加了番石榴依赖项和其他项目的依赖项。我想获得该项目的给定包的所有类,我已将其作为依赖项添加到我的pom中。 所以我尝试了这个:

public void getClassOfPackage() {

    final ClassLoader loader = Thread.currentThread()
            .getContextClassLoader();
    try {
        for (final ClassPath.ClassInfo info : ClassPath.from(loader)
                .getTopLevelClasses()) {

                System.out.println(info.getSimpleName());

        }
    } catch (IOException e) {
        e.printStackTrace();
    }

}

public static void main(String[] args) {
    new TestMain().getClassOfPackage();
}

我知道这是错误的,因为它在控制台中提供了这个:

HierarchicalConfigurationConverter
HierarchicalConfigurationXMLReader
HierarchicalINIConfiguration
SubsetConfiguration
SystemConfiguration...

我不知道我在哪里可以指定我正在谈论的项目,以及如何传递包名称,它给了我包含的所有类。

4 个答案:

答案 0 :(得分:1)

这就是为什么你看到它打印出sun.misc.Launcher$AppClassLoader

} else {
     System.out.println(loader.getClass().getName());
}

类路径中不在包中的每个类都会导致程序打印出您可能不想要的ClassLoader实现类的名称。

此外,虽然info.getName().startsWith("org.mypackage")应该有效,但最好还是写info.getPackageName().equals("org.mypackage")(或startsWith,如果你想要包含子包的话。)

答案 1 :(得分:0)

我可以显示同一个项目中的所有类,但是对于另一个在pom.xml中作为依赖项添加的项目尚未显示:

我们在同一个项目中的解决方案:

 public void getClassOfPackage() {

    final ClassLoader loader = Thread.currentThread()
            .getContextClassLoader();
    try {

        ClassPath classpath = ClassPath.from(loader); // scans the class path used by classloader
        for (ClassPath.ClassInfo classInfo : classpath.getTopLevelClasses("org.mypackage")) {
          System.out.println(classInfo.getSimpleName()+" <==> "+classInfo.getPackageName());
        }
    } catch (IOException e) {
        e.printStackTrace();
    }

}

public static void main(String[] args) {
    new TestMain().getClassOfPackage();
}

答案 2 :(得分:0)

我找到了两个解决方案:

使用番石榴:

public void getClassOfPackage(String packagenom) {

    final ClassLoader loader = Thread.currentThread()
            .getContextClassLoader();
    try {

        ClassPath classpath = ClassPath.from(loader); // scans the class path used by classloader
        for (ClassPath.ClassInfo classInfo : classpath.getTopLevelClasses(packagenom)) {
         if(!classInfo.getSimpleName().endsWith("_")){
            System.out.println(classInfo.getSimpleName());
            }
        }
    } catch (IOException e) {
        e.printStackTrace();
    }

}

public static void main(String[] args) {
    new TestMain().getClassOfPackage("org.myproject");
}

使用Java.util:

    public List<Class> getClassOfPackage(String packageName)
        throws ClassNotFoundException, IOException {

    ClassLoader classLoader = Thread.currentThread()
            .getContextClassLoader();

    assert classLoader != null;
    String path = packageName.replace('.', '/');
    Enumeration<URL> resources = classLoader.getResources(path);
    List<File> dirs = new ArrayList<File>();
    while (resources.hasMoreElements()) {
        URL resource = resources.nextElement();
        dirs.add(new File(resource.getFile()));
    }
    ArrayList<Class> classes = new ArrayList<Class>();
    for (File directory : dirs) {
        classes.addAll(findClasses(directory, packageName));
    }
    return classes;
}

private static List<Class> findClasses(File directory, String packageName)
        throws ClassNotFoundException {
    List<Class> classes = new ArrayList<Class>();
    if (!directory.exists()) {
        return classes;
    }
    File[] files = directory.listFiles();
    for (File file : files) {
        if (file.isDirectory()) {
            assert !file.getName().contains(".");
            classes.addAll(findClasses(file,
                    packageName + "." + file.getName()));
        } else if (file.getName().endsWith(".class")) {
            classes.add(Class.forName(packageName
                    + '.'
                    + file.getName().substring(0,
                            file.getName().length() - 6)));
        }
    }
    return classes;
}

public static void main(String[] args) throws ClassNotFoundException,
        IOException {

    for (Class className : new ClassOfPackage()
            .getClassOfPackage("org.mypackage")) {
        if (!className.getSimpleName().endsWith("_")) {
            System.out.println(className.getSimpleName());
        }

    }

}

答案 3 :(得分:-1)

Google reflections的帮助下解决此问题更容易。

请检查以下question以获取正确答案 - 请注意,选中的答案不提供有效的解决方案,第二个答案(AleksanderBlomskøld)确实如此!