Java 中的类加载器 (CL) 使用委托策略,这意味着 CL 首先会询问她的父级,后者也会询问她的父级,她是否知道类 X 的定义。只有当父级、任何祖先或当前类加载器知道 X 的类定义,然后当前类加载器将从相应X.class
文件加载定义。
如果一个类Foo
由系统类加载器加载,则任何Foo
依赖的类也需要由系统 CL 或该 CL 的父级加载。正如IDoMagic
其他 JAR 中提供的那样,您很可能需要将此 JAR 文件添加到类路径(java -cp ...
或java -jar ...
)中。由于委托模型,作为此 CL 的(大等)子级的任何 CL 也将获得对任何父级 CL 加载的类定义的访问权限。
如果IDoMagic
需要由自定义 CLFoo
加载,则不得由系统 CL 加载,而是使用自定义 CL 或此 CL 的子级加载,以便委托策略启动并提供IDoMagic
ifFoo
已加载/实例化的定义。
有一个自定义委托 CL 模型,其中共享类保存在一种公共 CL 列表/数组中,可以由依赖 CL 使用。依赖类不是公共 CL 的直接子类,而是委托 CL 的子类,委托 CL 只是在询问父类是否没有一个子类能够执行任务之前将调用委托给公共类。这里的一个解决方案可能是这样的结构:
bootstrap CL
- system CL
- delegation CL
- common CL
- plugin CL
- plugin 1 CL
- plugin 2 CL
在这里,委托 CL 需要将调用委托loadClass(...)
给findClass(...)
它所包含的公共 CL(对象组合),并且只有当它找不到定义时,才将调用委托给其父级。类似于这个仍然是实验课
此委托加载器可以IDoMagic
使用公共 CL fe 和Foo
具有插件加载器之一的类加载,该插件加载器不是common CL
. 但是,这要求delegation CL
在询问父级之前先对公共 CL 进行所有调用。此外,这个委托加载器给表带来了一些开销,因为它使自定义 CL 的优点之一(卸载未使用的类)更加困难。