Java内存模型

Java Memory Model (JMM)

一、对象的创建过程

首先类如果没有加载的话先进行加载,包括3个步骤:

1、class loading,将class加载到内存;

2、class linking,校验,将类的静态变量赋默认值,解析;

3、 class initializing,静态变量赋初始值,并执行静态代码块

然后创建对象:

1、申请对象内存

2、成员变量赋默认值

3、调用构造方法:将成员变量按顺序赋初始值,执行构造方法,首先要调用super构造方法。

二、对象布局

普通对象和数组对象的对象布局不同。

1、普通对象

1)对象头,markword,8个字节

2)ClassPointer 指针,-XX:+UseCompressedClassPointers 开启压缩为4个字节,不开启压缩为8个字节

3)实例数据,其中引用类型 -XX:+UserCompressedOops (Ordinary Object Pointers)开启压缩的话为4个字节,不开启压缩为8个字节,其他类型根据类型而定

4)Padding 对齐,8的倍数

2、数组对象

1)对象头,markword,8个字节

2)ClassPointer 指针,开启压缩为4个字节,不开启压缩为8个字节

3)数组长度,4个字节

4)数组数据

5)Padding 对齐,8的倍数

三、对象大小

所以new Object()大小是多少?

对象头,8个字节;ClassPointer指针,4或8个字节,如果4个字节,Padding补齐成8的倍数,所以总大写为8+4+4或者8+8=16个字节。

new int[] {} 大小是多少?

对象头,8个字节;ClassPointer指针,不开启压缩8个字节;数组长度4个字节;数据空;Padding补齐成8的倍数;总大小应该是8+8+4+4=24;如果开启压缩,8+4+4 = 16。

new M() 大小是多少?

class M {

       // 对象头,8个字节

       // ClassPointer 指针,开启压缩4个字节,不压缩8个字节,通过-XX:+UseCompressedClassPointers开启起作用

       int i; //4个字节

       String s; //引用类型,开启压缩4个字节,不压缩8个字节

       byte b; //1

       Object o; // 引用类型,开启压缩4个字节,不压缩8个字节;通过-XX:+UserCompressedOops开启压缩起作用

}

三、对象头组成

markword,在对象处于不同状态下存储的内容不同,比较复杂。对于64位的而言,根据锁状态具体如下:

1)无锁态,2位锁标志位01;1位是否偏向锁固定为0;是引用25位存储对象的hashCode,4位存储分代年龄。

2)轻量级锁,2位锁标志位00,另外存储指向栈中锁记录的指针

3)重量级锁,锁标志位为10,以及指向互斥量的指针

4)GC标记,11锁标志位

5)偏向锁,01锁标志位,是否偏向锁1位固定为1,另外包含线程ID,Epoch,分代年龄。

四、对象定位

对象定位有两种,句柄池和直接指针。

句柄池,通过间接指针,例如t = new T(),指向两个指针,一个指向对象,另一个指向t.class。

直接指针,直接指向对象。Hotspot 使用的是这种,效率比较高,可以直接找到对象。

  • 0
    点赞
  • 0
    收藏
    觉得还不错? 一键收藏
  • 0
    评论

“相关推荐”对你有帮助么?

  • 非常没帮助
  • 没帮助
  • 一般
  • 有帮助
  • 非常有帮助
提交
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值