首页 > 其他 > 详细

4、变量的本质含义、反编译和助记符详解

时间:2020-02-18 19:31:27      阅读:44      评论:0      收藏:0      [点我收藏+]

访问常量是否会引起类的初始化,关键要看常量的值是否在编译期间可以确定。

  1)如果常量的值可以在编译期间确定,则访问该常量时不会引起常量所在类的初始化;

    如:public static final String a = "parent";
    原因:常量的值在编译期间可以确定,则在编译阶段就会将【常量a的值】存入到调用方法所在类的常量池中。
本质上,调用常量的类并没有直接引用到定义常量的类,
  因此并不会触发定义常量类的初始化。

  2)如果常量的值不可以在编译期间确定,则访问该常量时会引起常量所在类的初始化;

    如:public static final String b = UUID.randomUUID().toString();
    原因:因为常量的值在编译期间无法确定,所以在编译阶段并不会将【常量b的值】存入到调用方法所在类的常量池中。因此程序在运行时,会主动使用常量b所在的类,
  导致该类的初始化。
package com.shtec.init;

import java.util.UUID;

/**
 * 【确定值的常量】在编译阶段会存入到调用这个常量的方法所在的类的常量池中,本质上,调用常量的类并没有直接引用到定义常量的类,因此并不会触发定义常量类的初始化。
 *     Parent2类中的【常量a】在编译阶段就已经放到了Demo2的常量池中,因此并不会将Parent2中的静态代码块打印出来
 * 
 * @author sunhao
 *
 */
public class Demo2 {
    
    public static void main(String[] args) {
        //编译阶段就会将a的值parent存入到Demo2的常量池中,所以在调用【Parent2.a】时,是直接从Demo2的常量池中取值,不会触发Parent2的初始化;
        System.out.println(Parent2.a);
        //输出
        //parent
        
        //编译阶段无法将b的值存入到Demo2的常量池中,所以在调用【Parent2.b】时,会主动使用Parent2这个类,因此会触发Parent2的初始化;
        System.out.println(Parent2.b);
        //输出
        //parent
        //e28f2c68-204e-474d-be01-cbda912a4836
    }
    

}
class Parent2{
    public static final String a = "parent";
    public static final String b = UUID.randomUUID().toString();
    static{
        System.out.println("Parent2 static block");
    }
}

 

4、变量的本质含义、反编译和助记符详解

原文:https://www.cnblogs.com/sunhao1234/p/12327303.html

(0)
(0)
   
举报
评论 一句话评论(0
关于我们 - 联系我们 - 留言反馈 - 联系我们:wmxa8@hotmail.com
© 2014 bubuko.com 版权所有
打开技术之扣,分享程序人生!