Java对象头
对象是什么
Java是一个面向对象的语言,在Java中可以使用new关键字来产生一个对象,但这个对象到底是什么,应该具有哪些属性?
首先跟我们自己先想下,Java对象已经有以下几个属性:
- 属于哪个类
- 有哪些字段和类型
对象的值
….在HotSpot虚拟机中,真实的Java对象是分成三个部分:
对象头
- 对象的值
- 对象的填充字节 (在JVM中,要求对象占用内存的大小应该是8bit的倍数,这个信息是用来补齐8bit的,无其他作用)
对象头
对象头是Java中对象都具有的属性,是jvm在编译和运行阶段读取的信息。对象头包含三个部分:
- mark word
- 指针向类的指针
数组的长度(只有数组的对象用到)
这3个中最复杂的是MarkWord,MarkWord用于存储对象自身的运行时数据,
如哈希码(HashCode)、GC分代年龄、锁状态标志、线程持有的锁、偏向线程ID、偏向时间戳等等。在32bit的环境中,Java头存储的信息如下
对象头的应用
————————————————————————-
偏向锁
在HotSpot的虚拟机中,当一个线程访问同步块并尝试获取锁时,会在对象头和栈帧中的记录里存储锁的偏向的线程ID,以后该线程进入和退出同步块的代码时候,不需要再进行加锁 ,只需要检测下MarkWord中的是否是当前线程的偏向锁。如果成功,则说明已经获得了锁,如果检测不成功,就再进行加锁。
轻量级锁
线程在执行同步块之前,JVM会现在当前的线程的栈帧中创建用于存储锁记录的空间,并肩对象头的MarkWord复制到锁的记录中,然后线程尝试将对象头MarkWord替换为指向锁记录的指针,如果不成功,说明锁存在竞争,当前线程开始进行盲等来获取锁。