Java虚拟机--一段Java程序的生命史(五)

  • 来源:
  • 更新日期:2018-05-23

摘要:准备阶段正式为类变量分配内存并设置初始值的阶段这些变量所使用的内存都在方法区进行分配。

 准备阶段正式为类变量分配内存并设置初始值的阶段这些变量所使用的内存都在方法区进行分配。

2-160Q0111130B2.jpg

解析
解析阶段是JVM将常量池内的符号引用替换为直接引用的过程前面我们谈到的编译填充符号表的价值在这地方体现出来了。解析过程无非就是对类或接口、字段、接口方法进行解析。
初始化
类初始化阶段是类加载过程的最后一步在准备阶段变量已经赋过一次初始值,而在这一步则会根据程序猿定制的要求进行初始化类变量和其他资源。
在这个阶段就是执行前面编译字节码生成流程提到的方法的过程。虚拟机也保证在多线程环境下这个方法被同时调用时被正确的加锁、同步保证只有一个线程去执行这个方法而其他线程阻塞等待。
这个位置还涉及到另一个我们比较关心的知识点Java何时触发对类的初始化操作呢?
在遇到new、getstatic、putstatic或invokestatic这4条字节码指令时如果类没有初始化、则需要触发其初始化。简单理解就是new一个对象的时候读取或者设置一个类的静态字段的时候调用一个类的静态方法的时候。使用java.lang.reflect包的方法对类进行反射调用的时候如果类没有初始化则需要触发其初始化。当初始化一个类发现其父类还没进行初始化则先触发其父类的初始化操作。当虚拟机启动时用户需要指定一个要执行的主类虚拟会先初始化这个主类。当使用JDK1.7以上的动态语言支持时如果一个java.lang.invoke.MethodHandle实例最后的解析结果为REF_getStatic、REF_putStatic、REF_invokeStatic的方法句柄,并且这个方法句柄所对应类没有进行初始化则触发初始化操作。