vlambda博客
学习文章列表

【Java基础巩固系列】Java双亲委派机制理解

【Java基础巩固系列】Java双亲委派机制理解


1.类加载过程

【Java基础巩固系列】Java双亲委派机制理解



# 2.JVM中的类加载器

①、启动类加载器(Bootstrap ClassLoader)

 负责将存放在 <JAVA_HOME>/lib 目录中的,或者被 -Xbootclasspath 参数所指定的路径中的,并且是虚拟机按照文件名识别的(仅按照文件名识别,如rt.jar,名字不符合的类库即使放在lib目录中也不会被加载)类库加载到虚拟机内存中。启动类加载器无法被Java程序直接引用。

 JDK 中的源码类大都是由启动类加载器加载,比如前面说的 java.lang.String,java.util.List等,需要注意的是,启动类 main Class 也是由启动类加载器加载。

②、扩展类加载器(Extension ClassLoader)

 这个类加载器由 sun.misc.Launcher$ExtClassLoader 实现,负责加载<JAVA_HOME>/lib/ext 目录中的,或者被 java.ext.dirs 系统变量所指定的路径中的所有类库。

开发者可以直接使用扩展类加载器。

③、应用程序类加载器(Application ClassLoader)

 由 sun.misc.Launcher$AppClassLoader 实现。由于这个类加载器是 ClassLoader.getSystemClassLoader() 方法的返回值,所以一般也称它为系统类加载器。

 它负责加载用户类路径ClassPath上所指定的类库,开发者可以直接使用这个类加载器。如果应用程序中没有自定义过自己的类加载器,一般情况下这个就是程序中默认的类加载器。

 通常项目中自定义的类,都会放在类路径下,由应用程序类加载器加载。

④、自定义类加载器(User ClassLoader)

 这是由用户自己定义的类加载器,一般情况下我们不会自定义类加载器,但有些特殊情况,比如JDBC能够通过连接各种不同的数据库就是自定义类加载器来实现的。

3.什么是双亲委派机制

 首先,我们设想一下,JAVA设计者为什么要使用和设计这种机制呢?

 如果有不法分子在你项目中构造了一个java.lang.String类,并在该类中植入了一些不良代码,但你自己浑然不知,以为使用的String类还是 rt.jar 包下的,那可能会给你系统造成不良的影响。聪明的Java虚拟机实现者也想到了这个问题,于是,他们引入了 双亲委派模型来解决这个问题。

接下来我们在看看双亲委派机制的实现过程:【Java基础巩固系列】Java双亲委派机制理解

说明:双亲委派机制就是如果一个类加载器收到了类加载请求,它首先不会自己尝试去加载这个类,而是把这个请求委派给父类加载器去完成,每一个层次的类加载器都是如此,因此所有的加载请求最终都应该传送到顶层的启动类加载器中,只有父类加载器反馈到无法完成这个加载请求(它的搜索范围没有找到这个类),子加载器才会尝试自己去加载。

 因此,上面提到的问题就可以被避免了。因为双亲委派机制会优先加载使用内置类库中的String类,而不会用到自定义的String类。

End