一个类从加载到使用,一般会经历下面的过程:
类加载--》验证--》准备--》解析--》初始化--》使用--》卸载
啥时候会从“.class”字节码文件中加载这个类到JVM内存里来?-->你的代码用到这个类的时候
概括一下,首先你的代码中包含“main()”方法的主类一定会在JVM进程启动之后被加载到内存,开始执行你的“main()”方法中的代码。接着遇到使用的类,就会从对应的“.class”字节码文件加载对应的类到内存里来。
【1】验证阶段
根据Java虚拟机规范,来校验你加载进来的".class”文件中的内容,是否符合指定的规范。
【2】准备阶段
验证之后,会进行准备阶段的工作,首先会给加载到内存中的这个类分配一定的内存空间,然后给他里面的类变量分配内存空间,来一个默认的初始值。
【3】解析阶段
准备阶段之后,解析阶段实际上是把符号引用替换为直接引用的过程。不做深入。
【4】初始化
准备阶段会给类变量开辟一个内存空间,然后给这个初始值0罢了。
赋值的代码会在初始化阶段来执行。
什么阶段会初始化一个类?
一般来说有几个时机,比如“new ReplicaManager()”来实例化类的对象了,此时就会触发类的加载到初始化的全过程,把这个类准备好,然后再实例化一个对象出来;如果初始化一个类的时候,发现他的父类还没有初始化,那么必须先初始化他的父类。
【5】类加载器和双亲委派机制
Java的类加载器
·【1】启动类加载器
Bootstrap ClassLoader,主要是负责加载我们在机器上安装的Java目录下的核心类的。在Java安装目录下,有一个lib目录,这里有Java最核心的一些类库,支撑你的Java系统的运行,一旦你的JVM启动,那么首先会依托启动类加载器,去加载你的Java安装目录下的lib目录中的核心类库。
·【2】扩展类加载器
Extension ClassLoader,这个类加载器就是加载lib/ext目录下的,支撑你的系统的运行。
·【3】应用程序类加载器
Application ClassLoader,这类加载器会负责加载“ClassPath”环境变量所指定的路径中的类。大致理解为你写好的那些代码。
·【4】自定义类加载器
还可以自定义类加载器,根据你的需求加载你自己的类
·【5】双亲委派机制
JVM类加载器是有亲子层级结构的,就是说启动类加载器是最上层的,扩展类加载器在第二层,第三层是应用程序类加载器,最后一层是自定义类加载器。
双亲委派机制:
就是假设你的应用程序类加载器需要加载一个类,他首先会委派自己的父类加载器去加载,最终传递到顶层的类加载器去加载。但是如果父类加载器在自己负责加载的范围内,没有找到这个类,那么就会下推加载权利给自己的子类加载器。比如JVM现在需要加载“Replica”类,此时应用程序类加载器会问问自己的爸爸,也就是拓展类加载器,你能加载到这个类吗?然后拓展类加载器直接问问自己的爸爸,启动类加载器,你能加载到这个类吗?启动类加载器心想,我在Java安装目录下,没有找到这类,自己找去。然后就下推加载权利给拓展类加载器这个儿子,结果拓展类加载器找了半天,也没有找到自己负责的目录中有这个类。然后应用程序类加载器就会在自己负责的范围内,比如就是你写好的那个系统打包成的jar包,然后就自己把这个类加载到内存里去了。这就是所谓的双亲委派机制,先找父亲去加载,不行的话再由儿子来加载。

网友评论