关于jdk8中静态变量与常量的存储位置

1,809 阅读1分钟

第三版的《深入浅出Java虚拟机》一书中,有这么一句话:JDK7及以后版本的HotSpot虚拟机选择把静态变量与类型在Java语言一端的映射Class对象存放在一起,存储于Java堆之中(P156),网上看到有的说存储于元空间中,为了验证说法,做了一个小小的实验。

首先设置以下属性

-XX:+PrintGCDetails -Xmx6M

贴上代码:

    public static final int _1MB = 1024 * 1024;

    public static byte[] allocation1 = new byte[2 * _1MB];
    public static byte[] allocation2 = new byte[2 * _1MB];
    public static byte[] allocation3 = new byte[2 * _1MB];
    public static byte[] allocation4 = new byte[2 * _1MB];

    public static void main(String[] args) {
//        Test test = new Test();
    }

显示老年代空间已满,内存溢出

之后把修饰符改为public static final,与上面出现同样的错误

设置以下属性

-XX:+PrintGCDetails -XX:MaxMetaspaceSize=6m

重复上面两次,显示用的是新生代的内存

改回第一次的设置,把static去掉,去掉注释,同样报堆空间不足的错误

结论:静态变量与常量随Class对象存储于Java堆中,实例常量随实例存储于堆中