双亲委派模型意义:
· 系统类防止内存中出现多份同样的字节码
· 保证Java程序安全稳定运行
层次关系如下图:
验证
类被加在后,就进入连接阶段。连接就是将已经读取到内存的类的二进制数据合并到虚拟机的运行时环境中去
准备
在准备阶段,Java虚拟机为类的静态变量分配内存,并设置默认的初始值,这些内存都将在方法区中分配。
对于该阶段有以下几点需要注意:
· 这时候进行内存分配的仅包括类变量(static),而不包括实例变量,实例变量会在对象实例化时随着对象一块分配在Java堆中。
· 这里所设置的初始值通常情况下是数据类型默认的零值(如0、0L、null、false等),而不是被在Java代码中被显式地赋予的值。
例如对一下Sample类,在准备阶段,将为int类型的静态变量a分配4个字节的内存控件,并赋予默认值0,为long类型的静态变量b分配8个字节的内存控件,并赋予默认值0;
public class Sample{ private static int a=1; private static int b; static{ b=2; } } |
解析
在解析阶段,Java虚拟机会把类的二进制数据中的符号引用替换为直接引用。例如在Worker类的gotoWork()方法中会引用Car类的run()方法。
public void gotoWork(){
car.run(); //这段代码在Worker类的二进制数据中表示为符号引用
}
在Worker类的二进制数据中,包含了一个对Car类的run()方法的符号引用,它由run()方法的全名和相关描述符组成。在解析阶段,Java虚拟机会把这个符号引用替换为一个指针,该指针指向Car类的run()方法区内的内存位置,这个指针就是直接引用。
初始化
类初始化阶段是类加载过程的最后一步,到了初始化阶段,才真正开始执行类中定义的java程序代码。在初始化阶段,Java虚拟机执行类的初始化语句,为类的静态变量 赋予正确的初始值。在程序中,静态变量的初始化有两种途径:
· 在静态变量的声明处进行初始化
· 在静态代码库中进行初始化
在如下代码中,静态变量a和b都被显示初始化,而静态变量c没有被显示初始化,它将保持默认值0;
public class Sample{ private static int a=1; private static int b; private static int c; static{ b=2; } } |
JVM初始化步骤:
· 假如这个类还没有被加载和连接,则程序先加载并连接该类
· 假如该类的直接父类还没有被初始化,则先初始化其直接父类
· 假如类中有初始化语句,则系统依次执行这些初始化语句
上文内容不用于商业目的,如涉及知识产权问题,请权利人联系博为峰小编(021-64471599-8017),我们将立即处理。