多个静态变量实例
Posted
tags:
篇首语:本文由小常识网(cha138.com)小编为大家整理,主要介绍了多个静态变量实例相关的知识,希望对你有一定的参考价值。
我正在尝试使用不同的类加载器来加载特定的类,并查看该类中的静态变量是否可以具有不同的实例。
基本上,我正在尝试编写Stephen C在this answer中提到的代码。
这是我的课程:
custom class loader.Java
class CustomClassLoader extends ClassLoader
{
public Class loadClass(String classname) throws ClassNotFoundException {
return super.loadClass(classname, true);
}
}
Test.java(包含驱动程序)
class Test {
public static void main(String[] args) throws Exception {
CustomClassLoader c1 = new CustomClassLoader();
CustomClassLoader c2 = new CustomClassLoader();
Class m1, m2;
m1 = c1.loadClass("A");
m2 = c2.loadClass("A");
m1.getField("b").set(null, 10);
System.out.println(m1.getField("b").get(null));
System.out.println(m2.getField("b").get(null));
}
}
A.java(包含静态变量)
class A {
public static int b = 5;
}
当我运行Test类时,我得到以下输出:
$ java Test
10
10
我希望输出为10和5.如何让代码创建我的静态变量的两个实例?
注意:我这样做只是为了实验和学习 - 但我很想知道是否可以有任何真实的应用。
看起来类似“A”类是由父类加载器加载的,而不是你的CustomClassLoader(因为你调用了super.loadClass)。
以下未经测试的修正应允许您使用自己的类加载器定义“A”类(同时将其他所有内容委托给父加载器)。
为可怕的小屋道歉,我假设单个inputStream.read()会读取所有内容!但你可以希望看到我的意思。
public Class loadClass(String classname) throws ClassNotFoundException {
if (classname.equals("A")) {
InputStream is = getResourceAsStream("A.class");
byte[] bodge = new byte[8192]; // Should read until EOF
try {
int len = is.read(bodge);
return defineClass("A", bodge, 0, len);
} catch (IOException e) {
e.printStackTrace();
}
}
return super.loadClass(classname, true);
}
你可能会最终得到ClasscastExceptions或类似的东西......
你的问题是new CustomClassLoader()
创建了一个类加载器,它将尝试将加载类委托给系统类加载器 - 对于这两个实例来说都是一样的。您的CustomClassLoader
甚至无法加载类本身。尝试使用URLClassLoader
并传递null
作为父母。
至于真实世界的应用程序:它对于Java Web容器和应用程序服务器至关重要,它允许不同的应用程序彼此完全隔离,即使它们可能使用许多相同的类。
如果你查看ClassLoader源甚至是javadoc,你会发现默认情况下ClassLoader委托给默认的系统ClassLoader,它实际上是在实例之间共享的。
我有同样的问题(集成测试)并尝试使用@Michael Borgwardt方法。这里有一些示例代码:
URLClassLoader classLoader1 = new URLClassLoader(new URL[]{new URL("file:///path/to/jar/my-classes.jar")}, null);
URLClassLoader classLoader2 = new URLClassLoader(new URL[]{new URL("file:///path/to/jar/my-classes.jar")}, null);
// Load with classLoader1
Class<?> myClass1 = classLoader1.loadClass("MyClass");
Constructor<?> constructor1 = myClass1.getConstructor();
Object instance1 = constructor1.newInstance();
// Load with classLoader2
Class<?> myClass2 = classLoader2.loadClass("MyClass");
Constructor<?> constructor2 = myClass2.getConstructor();
Object instance2 = constructor2.newInstance();
// Load with system classloader
MyClass myClass = new MyClass();
// ...
以上是关于多个静态变量实例的主要内容,如果未能解决你的问题,请参考以下文章