java findloadedclass_java – findLoadedClass()返回null

我做了一些测试,我很确定规范是否正确实施.我的错误在于反思性地加载类与将其作为解析步骤的一部分加载相同.这是有道理的:规范和JavaDoc都提到了类加载器的“记录”作为启动类加载器.如果我自己调用loadClass(),VM无法知道哪个类加载器应该是启动类加载器,因此定义的类加载器通常也会成为启动类加载器.

这可以通过将加载的类触发加载另一个类(foo.Baz)作为依赖项解析的一部分但是让另一个类加载器执行实际加载来证明.*

*我很确定这不是有效类加载器的正确行为.我这样做是为了说明一点.

考虑以下类(它们都在包foo中):

public class Bar {

public Bar() {

new Baz();

}

}

public class Baz {

}

我的自定义类加载器现在略有修改:

public class SimpleClassLoader extends ClassLoader {

static final String PATH = "/path/to/classes";

public SimpleClassLoader() {

// disable parent delegation

super(null);

}

public void printLoadedClass(String name) throws Exception {

Class> cls = findLoadedClass(name);

System.err.println("findLoadedClass(" + name + ") = " + cls

+ ", has class loader " + cls.getClassLoader());

}

@Override

protected Class> findClass(String name) throws ClassNotFoundException {

if (name.equals("foo.Baz")) {

// don't want to be defining class loader of foo.Baz

return getSystemClassLoader().loadClass(name);

}

// now we're loading foo.Bar

try {

byte[] b = IOUtils.toByteArray(new FileInputStream(PATH + "/foo/Bar.class"));

return defineClass(name, b, 0, b.length);

} catch (ClassFormatError | IOException e) {

e.printStackTrace();

throw new ClassNotFoundException();

}

}

}

测试很简单:

public static void main(String[] args) throws Exception {

SimpleClassLoader cl = new SimpleClassLoader();

Class> cls = cl.loadClass("foo.Bar");

cls.newInstance(); // this triggers resolution

cl.printLoadedClass("foo.Bar");

cl.printLoadedClass("foo.Baz");

}

输出是

findLoadedClass(foo.Bar) = class foo.Bar, has class loader foo.SimpleClassLoader@3a65724d

findLoadedClass(foo.Baz) = class foo.Baz, has class loader sun.misc.Launcher$AppClassLoader@1a2b2cf8

可以看出:SimpleClassLoader启动加载并定义foo.Bar.创建实例会触发foo.Baz的解析.这次,类的定义被委托给了系统类加载器,因此它成为定义类加载器.输出显示SimpleClassLoader正在为两个类启动类加载器,但仅定义第一个类.

  • 0
    点赞
  • 0
    收藏
    觉得还不错? 一键收藏
  • 0
    评论

“相关推荐”对你有帮助么?

  • 非常没帮助
  • 没帮助
  • 一般
  • 有帮助
  • 非常有帮助
提交
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值