zoukankan      html  css  js  c++  java
  • JVM 系列(一)类加载

    JVM 系列(一)类加载

    类加载机制是指把 class 文件加载到内存,并对数据进行校验、解析和初始化,最终形成 JVM 可以直接使用的 Java 类型的过程。

    ClassLoader 加载一个 class 文件到 JVM 时需要经过以下三个的步骤:

    图1.1 JVM加载类的三个步骤

    一、加载

    将 class 文件字节码内容加载到内存中,并将这些静态数据转换成方法区中的运行时数据构,在堆中生成一个代表这个类的 java.lang.Class 对象,作为方法区类数据的访问入口。

    二、链接

    将 Java 类的二进制代码合并到 JVM 的运行状态之中的过程。

    1. 验证:确保加载的信息符合 JVM 规范,没有安全方面的问题。

      字节码验证内容

    2. 准备:正式为类变量分配内存空间并设置初始值,常量的赋值也是在这一阶段进行的,这些内存都将在方法区中进行分配。

    3. 解析:虚拟机常量池内的符号引用替换为直接引用的过程。

    三、初始化

    初始化阶段是执行类构 () 方法的过程。类构造器 () 方法是由编译器自动收集类中的所有类变量的赋值动作和静态语句块(static块)中的语句合并产生的。

    1. 当初始化一个类的时候,如果发现其父类还没有进行过初始化,则需要先完成其父类的初始化。

    2. 虚拟机会保证一个类的 () 方法在多程环境中被正确加锁和同步。

    3. 当访问一个 Java 关的静态域时,只有真正声明这个域的类才会被初始化。

    类初始化时的死锁问题

    四、主动引用和被动引用

    那类在什么时候会被初始化呢?

    (1) 类的主动引用(一定会发生类的初始化)

    1. new 一个类的对象

    2. 调用类的静态成员(除了 final 常量)和静态方法

    3. 使同 java.lang reflect 包的方法对类进行反射调用

    4. 初始化子类时,要求先会初始化父类

    5. 当虚拟机启动时,先加载含 main() 方法在的类

    (2) 类的被动引用(不会发生类的初始化)

    1. 当访问一个静态域时,只有真正声明这个域的类才会初始化

      通过子类引用父类的静量,不会导致子类的初始化

    2. 通过数组定义类引用,不会触发类的初化

    3. 引用常量不会触发类的初始化(常量在编译阶段就存入调用类的常量池中了)

    class FinalFieldClass {
    
        public /*final*/ static String constString = "CONST";
    
        static {
            System.out.println("FinalFieldClass init");
        }
    }
    
    /**
     * -XX:+TraceClassLoading
     */
    public class UseFinalField {
        public static void main(String[] args) {
            System.out.println(FinalFieldClass.constString);
        }
    }
    

    constString 不使用 final 修辞时类 FinalFieldClass 被加载了:

    [Loaded com.github.binarylei.jvm.UseFinalField from file:/F:/doc/java/code-2018/disruptor/target/test-classes/]
    [Loaded com.github.binarylei.jvm.FinalFieldClass from file:/F:/doc/java/code-2018/disruptor/target/test-classes/]
    FinalFieldClass init
    CONST
    

    constString 使用 final 修辞时类 FinalFieldClass 没有被加载:

    [Loaded com.github.binarylei.jvm.UseFinalField from file:/F:/doc/java/code-2018/disruptor/target/test-classes/]
    CONST
    

    参考:

    本文转载至《实战JAVA虚拟机 JVM故障诊断与性能优化》


    每天用心记录一点点。内容也许不重要,但习惯很重要!

  • 相关阅读:
    18.综合应用判断素数
    17.综合应用判断素数
    16.综合应用判断素数
    15.for循环的三个表达式是可以省略
    14.循环的理解
    myeclipse2014中搭建SSH环境注意事项
    Java web设计模式学习
    问题1:myeclipse中导入新JSP项目出现红色感叹号
    Java集合类学习笔记
    Java 复习第一部分:知识体系、变量、运算部分
  • 原文地址:https://www.cnblogs.com/binarylei/p/9255905.html
Copyright © 2011-2022 走看看