JVM:Hotspot虚拟机中的对象

在HotSpot虚拟机中,对象在内存中存储的布局可以被分为3个区域:对象头(Header)、实例数据(Instance data)和对齐填充(Padding).对象头包括两部分信息,第一部分存储自身的运行时数据,如哈希值、GC分代年龄、锁状态标志、线程持有的锁、偏向锁ID、偏向时间戳等,这部分数据的长度在32位和64位的虚拟机中(未开启压缩指针)分别为32bit和64bit,官方称它为 Mark Word。

存储内容 标志位 状态
对象哈希码、对象分代年龄 01 未锁定
指向锁记录的指针 00 轻量级锁定
指向重量级锁的指针 10 膨胀(重量级锁定)
空,不需要记录信息 11 GC标记
偏向ID、偏向时间戳、对象分代年龄 01 可偏向

查找对象的元数据信息不一定要经过对象本身。如果对象是一个数组,对象头必须有一块记录数组长度的数据,但是从数组的元数据中却无法确定大小。

实例数据部分是对象真正存储的有效信息,也就是在程序中所定义各种类型的字段内容。无论是父类继承下来的,还是在子类中定义的。这部分会影响虚拟机分配策略参数和字段在Java源码中定义顺序的影响。

对齐填充并不是必然存在的,没有特别含义,仅仅是占位符的作用。对象的的大小必须是8字节的整数倍,示例数据没有满足8字节的倍数,则会填充补全。

对象的访问定位
建立对象是为了使用对象,Java程序需要通过栈上的reference数据来操作堆上的具体对象。reference类型是一个对象的引用,并没有规定是用何种定位、访问堆中对象的具体位置,
这些取决于虚拟机的实现。目前主流的访问方式有句柄直接指针两种。

  1. 若是用句柄的话,Java堆中会划分一块内存来作为句柄池,reference中存储的是对象的句柄地址,而句柄中包含对象实例数据对象类型数据的具体地址信息。
  2. 若是用直接指针(开销小,速度相对较快),那么Java堆对象就必须考虑放置访问对象类型数据的相关信息,而reference中存储的就是对象地址

原文地址:https://www.cnblogs.com/magic-sea/p/11614370.html

时间: 2024-10-06 22:02:01

JVM:Hotspot虚拟机中的对象的相关文章

【005】【JVM——Hotspot算法实现存活对象判定和垃圾收集】

Hotspot算法实现存活对象判断和垃圾收集 枚举根节点 作为GC Roots 的节点主要在全局性的引用(例如常量或类静态属性)与执行上下文(例如栈帧中的本地变量表)中,它们的数量庞大,逐个检查里面的引用,会消耗很多时间.其次,准确的可达性分析需要暂停用线程的执行. 目前的主流Java 虚拟机使用的都是准确式GC (准确式内存管理Exact Memory Management:虚拟机知道内存中某个位置的数据类型具体是什么),所以当执行系统停顿下米后, 并不需要一个不漏地检验所有执行上下文和全局的

java虚拟机中的对象的创建

当虚拟机遇到一条new 指令时,首先去检查这个指令的参数是否能在常量池中定位到一个类的符号引用,并且这个符号引用代表类的是否已加载.解析和初始化过.如果没有必须执行类的加载过程. 在类加载检查过后,接下来虚拟机将为新生对象分配内存.对象所需内存大小在类加载完成后便可完全确定,为对象分配空间的任务等同于把一块确定大小的内存从java堆中化分出来.java内存的分配方式分为"指针碰撞"(Bump the Pointer)和"空闲列表"(Free List)两种方式. 指

深入理解JVM:HotSpot虚拟机对象探秘

对象的创建 java是一门面向对象的语言.在Java程序执行过程中无时无刻有Java对象被创建出来.在语言层面上,创建对象(克隆.反序列化)一般是一个newkeyword而已,而在虚拟机中,对象的创建步骤例如以下: 1.当虚拟机遇到new指令时.首先将去检查这个指令參数能否在常量池中定位到一个类的引用符号,而且检查这个符号引用代表的类是否被载入.解析和初始化过.假设没有.那必须先执行相应的类载入过程. 2.在类载入检查通过以后.接下来虚拟机将为新生对象分配内存.对象所需的内存大小在类载入后便确定

HotSpot虚拟机对象探秘

一.对象的创建: 虚拟机遇到一条new指令时,首先将去检查这个指令的参数是否能在常量池中定位到一个类的符号引用,并且检查这个符号引用代表的类是否已被加载,解析和初始化过.如果没有,那必须先执行响应的类加载过程.对象所需内存的大小在类加载完成后便可完全确定,为对象分配空间的任务等同于把一块确定大小的内存从Java堆中划分出来. 对象空间分配方式:指针碰撞, 空闲列表 创建的步骤: 1.检查是否能在常量池中定位到一个类的符号引用,并且检查这个符号引用代表的类是否已被加载.解析和初始化过.如果没有必须

HotSpot虚拟机对象相关内容

一.对象的创建 1.类加载检查 普通对象的创建过程:虚拟机遇到一条new指令时,首先将去检查这个指令的参数是否能在常量池中定位到一个类的符号引用,并且检查这个符号引用代表的类是否已被加载.解析和初始化过.如果没有,那么必须先执行相应的类加载过程. 2.分配内存 分配内存时主要注意两个问题:1.如何分配空间.2.修改指针时如何实现线程安全. 如果内存是规整的,就使用"指针碰撞"的方式,即将空闲部分的指针移动对象内存大小相等的距离.如果内存不是规整的,虚拟机必须维护一个表,记录那些内存块可

【深入理解JAVA虚拟机】第二部分.内存自动管理机制.2.HotSpot虚拟机对象探秘

2.HotSpot虚拟机对象探秘 对象的创建过程 1.加载类 虚拟机遇到一条new指令时,首先将去检查这个指令的参数是否能在常量池中定位到一个类的符号引用,并且检查这个符号引用代表的类是否已被加载. 解析和初始化过. 如果没有,那必须先执行相应的类加载过程. 2.分配内存 在类加载检查通过后,接下来虚拟机将为新生对象分配内存. 对象所需内存的大小在类加载完成后便可完全确定为对象分配空间的任务等同于把一块确定大小的内存从Java堆中划分出来. 分配方式: 1.指针碰撞.适用于连续内存,需要垃圾回收

第二章:Hotspot虚拟机对象

对象创建 虚拟机遇到一个new指令时,首先去,检查这个指令的参数是否在常量池中定位到一个雷的符号引用,并且检查这个符号引用代表的雷是否已被加载.解析.初始化过. 在类加载检查通过后,虚拟机将会为新对象分配内存,对象所需要的内存大小在加载后可以确定,为对象分配内存的任务就是把一块确定大小的内存从Java堆中划分出来. 假如堆时绝对规整的,所有用过的内存放在一边,空闲的内存放在另一边,中间放着一个指针作为分界点的指示器,那么分配内存就仅仅是把那个指针指向空闲空间的那边挪动一段和对象大小相等的距离.这

JVM系列之七:HotSpot 虚拟机

1. 对象的创建 1. 遇到 new 指令时,首先检查这个指令的参数是否能在常量池中定位到一个类的符号引用,并且检查这个符号引用代表的类是否已经被加载.解析和初始化过.如果没有,执行相应的类加载. 2. 类加载检查通过之后,为新对象分配内存(内存大小在类加载完成后便可确认).在堆的空闲内存中划分一块区域(‘指针碰撞-内存规整’或‘空闲列表-内存交错’的分配方式). A.假设Java堆是规整的,所有用过的内存放在一边,空闲的内存放在另外一边,中间放着一个指针作为分界点的指示器.那分配内存只是把指针

【JVM】虚拟机类加载机制

什么是类加载 虚拟机把描述类的数据从Class文件加载到内存,并对数据进行校验.转换解析和初始化,最终形成可以被虚拟机直接使用的Java类型,这就是虚拟机的类加载机制. <[JVM]类文件结构>讲的是Class文件结构,即我们编写的Java代码(.java文件)经过编译后生成Class文件(.class文件).这一章讲述的是如何将这个Class文件加载到内存并最终形成虚拟机直接使用Java类型的过程. 1.类加载的时机 类的生命周期 类的生命周期 其中,加载.验证.准备.初始化和卸载这5个顺序