【问题标题】:Java - Strange behaviour with dynamic class loaderJava - 动态类加载器的奇怪行为
【发布时间】:2016-12-22 00:09:52
【问题描述】:

在我的代码中,我想从 Jar 文件中动态加载 Module 类的实现。

在我的目录中,我有 3 个文件:A.jar、B.jar、C.jar 每个 jar 都有一个名为 Main 的类,它扩展了 Module 类

A.jar 代码示例:

public class Main extends Module {

    private static String name = "A";

    public Main() {
        super(name);
    }

}

(B 和 C 文件相同,但在 name 属性中使用“B”和“C”而不是“A”)。

我的模块类代码是:

public abstract class Module{

    private StringProperty nameProperty;

    public Module(String name){
        this.nameProperty = new SimpleStringProperty(name);
    }

    public StringProperty nameProperty(){
         return nameProperty;
     }

}

这是我用来动态加载三个类的代码:

for (File moduleFile : Data.modulesDir.listFiles()) {

        try {

            URL url = moduleFile.toURI().toURL();
            Class[] parameters = new Class[] { URL.class };
            URLClassLoader sysLoader = (URLClassLoader) ClassLoader.getSystemClassLoader();
            Class<URLClassLoader> sysClass = URLClassLoader.class;

            Method method = sysClass.getDeclaredMethod("addURL", parameters);
            method.setAccessible(true);
            method.invoke(sysLoader, new Object[] { url });

            Constructor<?> cs = ClassLoader.getSystemClassLoader().loadClass("com.ehzlab.webreaper.module.Main")
                    .getConstructor();
            Module instance = (Module) cs.newInstance();

            System.out.println(instance.nameProperty.get());

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

    }

我期待这个输出:

A
B
C

但我得到了这个:

A
A
A

似乎在每次文件列表迭代时加载相同的 jar。但是调试时我注意到 URL 每次都会改变。 我也尝试过颠倒顺序,例如,将 B.jar 放在另一个 jar 之前,输出为:

B
B
B

为什么?

【问题讨论】:

  • 你不能在同一个类加载器中多次获得具有相同完全限定名的类。

标签: java jar classloader


【解决方案1】:

仅仅是因为您每次都使用相同的类加载器,它不会重新加载底层类:

ClassLoader.getSystemClassLoader()...

为了访问特定的类,您必须使用适当的类加载器来加载特定的jar 文件(可能是sysLoader,不确定,因为我没有检查):

Constructor<?> cs = sysLoader.loadClass("com.ehzlab.webreaper.module.Main")
                    .getConstructor();

也看看这个问题:How should I load Jars dynamically at runtime?

【讨论】:

猜你喜欢
  • 2011-02-14
  • 1970-01-01
  • 1970-01-01
  • 1970-01-01
  • 1970-01-01
  • 1970-01-01
  • 1970-01-01
  • 1970-01-01
  • 1970-01-01
相关资源
最近更新 更多