Java 对象(数组)占多大空间(几个字节) 手把手做实验

废话不多说,一起开干

1 前置知识

本次实验基于jdk8 64位以及以上版本。本机环境为jdk11
在这里插入图片描述
先查看一下jvm启动的默认参数,里面有2个参数值对本次实验会造成影响。
命令行: java -XX:+PrintCommandLineFlags -version 查看jvm默认参数
在这里插入图片描述

分别是 -XX:+UseCompressedOops 和 -XX:+UseCompressedClassPointers
这2个参数都是默认开启(+代表开启,-代表关闭)

UseCompressedOops:普通对象指针压缩(oop是ordinary object pointer的缩写),
UseCompressedClassPointers:类型指针压缩。

从字面意思很容易理解。
举个例子说明一下: Object o = new Object();
o指向new Object()的引用就是“普通对象指针”,
new Object()自身还需要指向Object类型的引用,也就是"类型指针"。

这2个压缩参数可以有4种组合(++, --, + -, -+),但有1种组合是会抛出警告的:

-XX:+UseCompressedClassPointers -XX:-UseCompressedOops,不要使用这种参数组合,用这种参数启动jvm时会抛出警告。

原因是jvm层面的hotspot源码对jvm的参数组合做了限制,一看就懂:

在这里插入图片描述
请大家有个印象,这2个参数在开启压缩时是占4个字节,关闭压缩时是占8个字节。马上开始进行我们的实验。

2 对象的内存存储布局

在这里插入图片描述
下面使用JOL库(Java Object Layout)来分析查看对象的内存布局,JOL库是openjdk中分析JVM中对象布局的工具库。

新建1个maven项目,引入

<dependency>
  <groupId>org.openjdk.jol</groupId>
  <artifactId>jol-core</artifactId>
  <version>0.9</version>
</dependency>

依赖即可使用。

2.1 使用默认参数-XX:+UseCompressedClassPointers -XX:+UseCompressedOops开启压缩启动程序,打印出Person对象的内存布局,进行详细说明。

在这里插入图片描述
Person对象合计占用32字节。

2.2 使用参数关闭压缩-XX:-UseCompressedClassPointers -XX:-UseCompressedOops启动程序,打印出Person对象的内存布局,进行对比说明

在这里插入图片描述

Person对象合计占用40字节。

3 数组的内存存储布局

在这里插入图片描述

使用默认参数-XX:+UseCompressedClassPointers -XX:+UseCompressedOops启动程序,打印出数组对象的内存布局,进行详细说明。
在这里插入图片描述
new Long[5]占用40字节,new long[5]占用56字节。

关闭指针压缩参数的例子就不详细再写了,各位可以自行尝试。

关于boolean值(比较特殊的基本类型)也做了实验,大家可以自己分析下,看和自己设想的是否一致:
在这里插入图片描述
同时也可以利用jol库对自己其他想验证的想法进行试验验证。

demo示例代码, 需要的自取: https://github.com/wanjinyu1988/joldemo.git

参考资料: 马士兵教育公开课

欢迎关注我的微信公众号: wanjinyu的技术小窝

发布了1 篇原创文章 · 获赞 0 · 访问量 285

猜你喜欢

转载自blog.csdn.net/weixin_40865973/article/details/105390202
今日推荐