0

我有 3 个 Java 项目 A、B 和 C。B 就像 A 的附加组件。A 和 B 对于某些类都依赖于项目 C。

现在在项目 A 中,当我使用 URLClassLoader 时,如下所示:

URLClassLoader ucl = new URLClassLoader(urls); //urls are paths to some classes in B

现在使用这些 ucl 时,当我在 B 中调用一些方法时,它给了我No Class Definition found exception。这是针对 C 类的。

现在,当我使用 ClassLoader 时,如下所示:

ClassLoader classLoader = Thread.currentThread().getContextClassLoader();
URLClassLoader ucl = new URLClassLoader(urls, classLoader);

当我调用 B 中的方法时,这很好用。我的问题:

1)当我以第一种方式执行时,正在使用哪个 ClassLoader?我阅读了 JavaDocs,但找不到任何可以解释的内容。
2)有没有办法获得一个特定于项目B的ClassLoader,我可以以某种方式使用它,这样我就不会遇到任何依赖问题?

谢谢你的帮助。

4

2 回答 2

1

默认的类加载器是系统类加载器(加载类路径上的类)。

如果您使用特定的类加载器在 B 中加载了类,请使用该实例。否则someTypeInB.getClass().getClassLoader()将作为一个黑客。

(注意: usingURLClassLoader.newInstance通常比 更可取new URLClassLoader,因为它增加了与不受信任的代码一起使用所必需的安全措施(尽管还不够)。此外,使用线程上下文类加载器通常是一个坏主意 - 您引入了对本地部分的依赖然而,线程被设置和使用的代码[无论如何可能没有任何一致的策略应用于它]。)

于 2011-10-04T18:47:11.693 回答
1

当您使用您的第一个 URLClassLoader 时,该 URLClassLoader 仅使用 B 的路径进行初始化,那么如果 B 中的某些内容需要解析 C 中的某些内容才能加载,那么它将出现问题。通过使用第二种形式,您是在说“如果在这里找不到您需要的东西,请查看'父'类加载器。” 这使得 C 得到解决,每个人都很高兴。

(要理解,唯一可以在不引用其他类的情况下加载的类是 Object ——即使这样也有点牵强。不仅仅是你需要引用该类的超类——至少,基础 JDK 中的对象可以通过即使没有父 CL,系统类加载器 - 但是如果您调用另一个类的任何方法或操作指向另一个类的指针或任何类似的东西,您需要解析该引用的类。)

于 2011-10-04T18:47:22.630 回答