博客
关于我
强烈建议你试试无所不能的chatGPT,快点击我
JVM 编译优化 静态常量会被添加到当前类的“常量池”中,无需加载引用类(常量不加载/常量找不到/常量不更新)
阅读量:4216 次
发布时间:2019-05-26

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

标题有点绕,意思是说如果A类中定义了一个常量,且这个常量是一个“编译期常量”,那么当其他类在引用这个常量的时候。A类本身可以不被JVM加载,这个常量可以被直接引用。

是不是更绕了,怎么还多出来一个“编译期常量”。即在编译期即可确定常量值。直接说重点,JVM这个编译优化会引起令人匪夷所思的BUG。让你查也查不到。

还是要回到标题,不加载A类就能直接引用A类的常量。这个常量会被存在调用类的常量池中。这样很容易让我想到既然是在编译期就存到了调用类中,那么如果编译的时候和运行的时候A类发生了变化,常量的值变了,在调用类没有重新编译的情况下,调用类就会引用到一个错误常量值。JVM真的会让这种事发生吗?!

用代码说话:

/** * @Author: tiantao * @Date: 2019/1/16 10:37 AM * @Version 1.0 */public class StaticClass {    static {        System.out.println("StaticClass loading...");    }    public static String VALUE = "static value loading A";    public static final String FIANL_VALUE = "fianl value loading A";}
/** * @Author: tiantao * @Date: 2019/1/16 10:38 AM * @Version 1.0 */public class StaticClassLoadTest {    public static void main(String[] args) {        System.out.println("StaticClassLoadTest...");        printStaticVar();    }    private static void printStaticVar() {        System.out.println(StaticClass.FIANL_VALUE);        System.out.println(StaticClass.VALUE);    }}

执行结果:

StaticClassLoadTest...fianl value loading AStaticClass loading...static value loading A

说明一下 StaticClass类的FIANL_VALUE是静态常量 而 VALUE 只是静态变量 或者说类变量。

从输出结果可以看出 在打印FIANL_VALUE的时候并没有加载StaticClass类,而是在需要调用到类变量的时候才加载的。

以上只是说明了加载顺序,但是不能说明静态常量 也就是例子中的FIANL_VALUE是被放到了调用类StaticClassLoadTest的常量池中。

接下来我们做如下操作。

1.备份当前的StaticClass的class文件。

2.修改StaticClass

/** * @Author: tiantao * @Date: 2019/1/16 10:37 AM * @Version 1.0 */public class StaticClass {    static {        System.out.println("StaticClass loading...");    }    public static String VALUE = "static value loading B";    public static final String FIANL_VALUE = "fianl value loading B";}

执行结果:

StaticClassLoadTest...fianl value loading BStaticClass loading...static value loading B

这个结果毋庸置疑,没毛病。

3.删除现在的StaticClass.class文件

4.将之前备份的StaticClass的副本.class重命名为:StaticClass.class

5.执行程序,看执行结果,见证奇迹:

StaticClassLoadTest...fianl value loading BStaticClass loading...static value loading A

怎么可以这样!

曾经那个修改常量不生效的bug,本地测试怎么都不复现,一上生产死活不生效。我明明没有改调用类,谁知道调用者也要更新!

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

你可能感兴趣的文章
JavaScript 学习网站
查看>>
cocos2dx java调用c++ -- 字符串传递
查看>>
CCScaleTo与CCScaleBy比较
查看>>
cocos2dx CCObject引用计数,内存释放分析(1)
查看>>
cocos2dx2.X 编译时,传递编译选项
查看>>
ccCArray.cpp 文件
查看>>
cocos2dx 屏幕大小
查看>>
libgdx: 2D Particle Editor工具使用
查看>>
eclipse 给jar库添加源码
查看>>
3.0正式版环境搭建(4)-- 运行(3)创建的工程
查看>>
C++ 枚举声明 enum 和 enum class
查看>>
Python optionParser模块的使用方法
查看>>
android 消灭星星出错
查看>>
PyCharm 教程(三)Hello world!
查看>>
PyCharm: 显示源码行号
查看>>
cocos2dx使用第三方字库.ttf,需要注意的事项
查看>>
cocos2dx 音频模块分析(4): 音效部分
查看>>
cocos2dx 音频模块分析(5): 音效部分
查看>>
19、Cocos2dx 3.0游戏开发找小三之Action:流动的水没有形状,漂流的风找不到踪迹、、、
查看>>
cocos2.X版本lua端使用定时器的方法
查看>>