JVM学习笔记12——类加载器与类初始化深度剖析
发布日期:2021-06-29 01:18:50 浏览次数:2 分类:技术文章

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

public class MyTest8 {    public static void main(String[] args){        System.out.println(FinalTest.x);    }}class FinalTest {    public static final int x = 3;    static {        System.out.println("FinalTest static block");    }}

不会输出静态代码块的文字,说明FinalTest没有被初始化,常量x放入了MyTest8的常量池中

public static int x = 3; //没有进入常量池public static final int x = new Random().nextInt(3); //运行期才会确定

上面两种情况会输出文字FinalTest static block

class Parent {    static int a = 3;    static {        // 2        System.out.println("Parent static block");    }}class Child extends Parent {    static int b = 4;    static {        // 3        System.out.println("Child static block");    }}public class MyTest9 {    static {        // 1        System.out.println("MyTest9 static block");    }    public static void main(String[] args){        System.out.println(Child.b);    }}

依次输出:

MyTest9 static block

Parent static block

Child static block

4

class Parent2 {    static int a = 3;    static {        System.out.println("Parent2 static block");    }}class Child2 extends Parent2 {    static int b = 4;    static {        System.out.println("Child2 static block");    }}public class MyTest10 {    static {        System.out.println("MyTest10 static block");    }    public static void main(String[] args){        Parent2 parent2; // 不会导致任何输出        System.out.println("***************");        parent2 = new Parent2();        System.out.println("***************");        System.out.println(parent2.a); // 只初始化一次        System.out.println("***************");        System.out.println(Child2.b);    }}

输出:

MyTest10 static block

***************
Parent2 static block
***************
3
***************
Child2 static block
4

class Parent3 {    static int a = 3;    static {        System.out.println("Parent3 static block");    }    static void doSomething(){        System.out.println("Parent3 doSomething");    }}class Child3 extends Parent3 {    static {        System.out.println("Child2 static block");    }}public class MyTest11 {    public static void main(String[] args){        System.out.println(Child3.a); // 因为a是父类的,虽然通过子类访问,但是表示的是对父类的主动使用        System.out.println("*************");        Child3.doSomething();    }}

输出

Parent3 static block

3
*************
Parent3 doSomething

子类调用父类的静态方法也不会导致子类的初始化,属于对父类的主动使用

/** * 调用ClassLoader类的loadClass方法加载一个类,并不是对类的主动使用,不会导致类初始化 */class CL {    static {        System.out.println("Class CL");    }}public class MyTest12 {    public static void main(String[] args) throws Exception{        ClassLoader loader = ClassLoader.getSystemClassLoader();        // 不会导致类的初始化        Class
clazz = loader.loadClass("com.yshuoo.jvm.classloader.CL"); System.out.println(clazz); System.out.println("******************"); // 反射属于主动使用,会导致类的初始化 clazz = Class.forName("com.yshuoo.jvm.classloader.CL"); System.out.println(clazz); }}

输出:

class com.yshuoo.jvm.classloader.CL

******************
Class CL
class com.yshuoo.jvm.classloader.CL

转载地址:https://blog.csdn.net/yshuoo/article/details/116501490 如侵犯您的版权,请留言回复原文章的地址,我们会给您删除此文章,给您带来不便请您谅解!

上一篇:JVM学习笔记13——不同的类加载器作用于加载动作分析
下一篇:JVM学习笔记11——类加载器双亲委托机制详解

发表评论

最新留言

表示我来过!
[***.240.166.169]2024年04月25日 05时24分22秒