tuc*_*uxi 6 java classloader dependency-management
我有一个依赖于库 X 的实用程序类 U,并且必须放入一个包中,该包将在具有 X 可用的程序(它应该执行其正常操作)和没有 X 的地方(它不应该执行任何操作)中使用。在不将类分成两部分的情况下,我找到了一个简单的模式来解决这个问题:
package foo;
import bar.MisteriousX;
public class U {
static private boolean isXPresent = false;
static {
try {
isXPresent = (null != U.class.getClassLoader().loadClass("bar.MisteriousX"));
} catch (Exception e) {
// loading of a sample X class failed: no X for you
}
}
public static void doSomething() {
if (isXPresent) {
new Runnable() {
public void run() {
System.err.println("X says " + MisteriousX.say());
}
}.run();
} else {
System.err.println("X is not there");
}
}
public static void main(String args[]) { doSomething(); }
}
Run Code Online (Sandbox Code Playgroud)
使用此模式,U 需要存在 X 才能编译,但在存在或不存在 X 的情况下运行时都会按预期工作。除非对 X 库的所有访问都在内部类内部,否则此代码将引发类加载器异常。
问题:导入解析是否保证在任何地方都能像这样工作,或者它取决于 JVM/ClassLoader 实现吗?这有既定的模式吗?上面的代码片段是否太老套而无法投入生产?
一般来说,当一个类第一次加载时,如果它引用了一个不存在的类,则可能会导致错误。所以是的,让一个类进行检查,而另一个类在没有反射的情况下实际访问外部包将按预期工作,至少在我迄今为止看到的所有实现上是这样。它不一定是内部类。
\n\nJVM 规范中的链接部分为实现提供了很大的自由度。如果您不使用两类方法,那么使用急切链接的实现中的验证将导致尝试加载,从而导致. 规范不要求对引用类进行验证,但也不禁止这种早期验证。但它确实要求U XLinkageError
\n\n\n解析期间检测到的任何错误都必须在程序中(直接或间接)使用对类或接口的符号引用的点处抛出。
\n
似乎您应该可以安全地假设仅当您实际访问内部类时才会引发错误。如果你看看这个答案的历史,你会发现我已经两次改变了我的观点,所以不能保证我这次读得正确\xe2\x80\xa6 :-/
\n| 归档时间: |
|
| 查看次数: |
2572 次 |
| 最近记录: |