博客
关于我
52. 什么时候会发生类初始化?
阅读量:561 次
发布时间:2019-03-09

本文共 1404 字,大约阅读时间需要 4 分钟。

什么时候会发生类的初始化?

类的初始化通常在以下场景中会发生:

  • 当虚拟机启动时,首先会初始化main方法所在的类
  • 当使用**new关键字**创建一个类的对象时。
  • 当调用类的静态成员(除了final常量**)和静态方法**时。
  • 当通过**java.lang.reflect**包中的方法对类进行反射调用时。
  • 当初始化一个类的子类时,子类会依次初始化其父类(如果父类未被初始化则会先初始化父类)。

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

以下情况会导致主动引用,从而传触发类初始化:

  • 当虚拟机启动时,首先会初始化main方法所在的类
  • new操作符:创建类对象时会引发类的初始化。
  • 静态方法和静态变量:调用类的静态成员会触发类的初始化,包括**static块**。
  • 反射调用:通过反射获取类及其成员并执行操作会触发类的初始化。
  • 子类初始化:当一个类被创建时,如果其父类未被初始化,则会先初始化父类。
  • 类的被动引用(不会发生类的初始化)

    以下情况不会引起类的初始化:

  • 通过子类引用父类的静态变量:例如,访问父类的静态变量不会触发子类的初始化。
  • 数组定义引用的类:如**Son[] array = new Son[5];**不会触发类的初始化。
  • 引用常量:常量在链接阶段已经静态存入类的常量池中,因此不会触发类的初始化。
  • 测试类何时被加载?

    以下代码片段可以帮助理解类何时会被初始化:

    package com.zfy.es.myes;public class T1 {    static {        System.out.println("main类被加载");    }    public static void main(String[] args) throws ClassNotFoundException {        //1. 主动引用        Son son = new Son();        // 反射调用不会导致类加载        // Class.forName("com.zfy.es.myes.Son");        //2. 被动引用:不会引起类的加载        // System.out.println(Son.b);        // 数组格式不会导致类加载        // Son[] array = new Son[5];        // 常量不会触发父类与子类的初始化        // System.out.println(Son.M);    }    class Father {        static int b = 2;        static {            System.out.println("父类被加载");        }    }    class Son extends Father {        static {            System.out.println("子类被加载");        }        static int a = 100;        static final int M = 1;    }

    输出结果

    • 父类被加载
    • main类被加载
    • 子类被加载

    当运行上述代码时,输出结果依次为:父类被加载 → main类被加载 → 子类被加载

    转载地址:http://alrpz.baihongyu.com/

    你可能感兴趣的文章