HotSpot虚拟机对象探秘(对象创建,对象内存布局,对象访问定位)
以常用的HotSpot虚拟机和JAVA内存区域堆为例,探讨对象的创建,对象的内存布局以及对象的访问定位
一.对象的创建
1)类加载:虚拟机遇到一条new指令时,先检测这个指令的参数能否在常量池中定位到一个类的符号的引用,并检查这个符号代表的类否收以及被加载,解析和初始化,如果没有那么就必须执行相应的类加载过程
2)分配内存:如果java堆的内存是绝对规整的,那么采用指针碰撞的方式分配内存,即所有空闲的内存放一边,不空闲的内存放一边,中间放着一个指针作为分界点的指示器,分配内存就仅仅是把那个指针向空闲的空间那边挪动一段与对象大小相等的距离,如果java堆的内存是不规整的话,那么我们必须维护一个空闲列表,记录哪些内存块是可用的,在分配的时候从列表中找到一个足够大的空间划分给对象实例,并更新列表上的记录
3)初始化:都初始化为0(不包括对象头),这一步操作保证了对象的实例字段在java代码中可以不赋初始值就直接使用
4)对象头的设置:对象是那个类的实例,如何找到类的元数据,对象的哈希码,对象的GC分代年龄,以及是否启动偏向锁等
5)程序员按照自己的意愿进行对象初始化
思考:对象的创建在虚拟机中是频繁的行为,如何保证并发情况下的线程安全呢?
比如正在给对象A分配内存,指针还没有来得及修改,对象B又同时使用了原来的指针分配内存
解决方案:
1)对分配内存空间的动作进行同步:实际上虚拟机采用CAS配上失败重试的方式保证更新操作的原子性
2)把内存分配的动作按照线程的不同划分在不同的空间进行:每个线程在java堆中预先分配一块内存,称为本地线程分配缓存TLAB,那个线程需要分配内存,就在那个线程的TLAB上分配,只用TLAB分配完并分配先新的TLAB时,才需要同步锁定
二.对象的内存布局
在HotSpot虚拟机中,对象在内存区域中存储布局可以分为3个区域:对象头,实例数据,对齐补充
对象头:又分为Mark Word和类型指针,Mark Word存储哈希码,GC分代年龄,锁状态标志,线程持有的锁,偏向线程ID,偏向时间戳等
,类型指针即对象指向它的类元数据的指针,虚拟机通过这个指针确定这个对象是哪个类的实例
实例数据:对象真正储存的有效信息,也就是在程序代码中所定义的各种类型的字段内容,无论是从父类继承来的,还是在子类中定义的,都需要记录来
对齐补充:并不是必然存在的,因为HotSpot要求对象的起始地址必须是8字节的整数倍,也就是对象的大小必须是8字节的整数倍,而对象头部分正好是8字节的整数倍,所以当对象的实例数据部分没有对齐时,就需要通过对齐补充来补全
三.对象的访问定位
java程序通过栈上的reference数据来操作堆上的具体对象,由于reference类型在java虚拟机规范中只规定了一个指向对象的引用,并没有定义这个引用应该通过何种方式去定位从而访问堆中的对象元素的具体位置,所以对象的访问方式是取决于虚拟机实现的,目前主流的方式有使用句柄和直接指针两种
句柄方式:堆中划分一块内存作为句柄池,reference中储存的就是对象的句柄地址,而对象的句柄地址中包含了对象的实例数据与类型数据各自具体的地址信息
直接指针:reference中储存的就是对象地址,java堆对象的布局需要考虑如何放置访问类型数据的相关信息
优劣分析:
1.使用句柄的最大好处就是reference中储存的是稳定的句柄地址,在对象被移动(垃圾收集时对象移动是非常普遍的行为)时只会改变句柄中实例数据指针,而refrence本身不需要修改
2.直接指针访问最大好处就是速度更快,节省了一次指针定位的时间开销,由于对象的访问在java中非常频繁,积累下来也是一笔很大的时间开销
参考书籍:深入理解JAVA虚拟机 java高级特性与最佳实践 第二版
HotSpot虚拟机对象探秘(对象创建,对象内存布局,对象访问定位)的更多相关文章
- 浅谈Java虚拟机内存中的对象创建,内存布局,访问定位
参考于 深入理解Java虚拟机 这里介绍HotSpot虚拟机(自带的虚拟机) 1.对象的创建 对于程序员来说,创建对象的方法: User user1 = new User(); User user2 ...
- Java对象的创建、内存布局和访问定位
在Java运行时数据区中,我们知道了虚拟机内存的概况,本文介绍虚拟机内存中的数据的其它细节,如对象如何创建.如何布局以及如何访问. 基于实用的原则,这里以HotSpot虚拟机和常用的内存区域Java堆 ...
- 【深入理解JVM】:Java对象的创建、内存布局、访问定位
对象的创建 一个简单的创建对象语句Clazz instance = new Clazz();包含的主要过程包括了类加载检查.对象分配内存.并发处理.内存空间初始化.对象设置.执行ini方法等. 主要流 ...
- java面试-对象的创建、内存布局、访问定位
一.对象的创建 1.虚拟机遇到一条new指令时,首先将去检查这个指令的参数是否能在常量池中定位到一个类的符号引用,并且检查这个符号引用代表的类是否已被加载.解析和初始化过.如果没有,那必须先执行相应的 ...
- 深入理解Java虚拟机(二)、Java对象的创建,内存布局和访问定位
对象的创建: Object obj = new Object(); 常量池中是否有Ljava.lang.Object
- 【JVM之内存与垃圾回收篇】对象实例化内存布局与访问定位
对象实例化内存布局与访问定位 从各自具体的内存分配上来讲 new 的对象放在堆中 对象所属的类型信息是放在方法区的 方法当中的局部变量放在栈空间 这 new 的对象怎么把三块粘合到一起 就是这章的内容 ...
- JVM 专题十二:运行时数据区(七)对象的实例化内存布局与访问定位
1. 对象的实例化 1.1 创建对象的方式 new 最常见的方式 变形1 : Xxx的静态方法 变形2 : XxBuilder/XxoxFactory的静态方法 Class的newInstance() ...
- JVM运行时数据区--纵向补充--对象的实例化内存布局与访问定位
对象的实例化 创建对象的方式 1.new:最常见的方式(本质是构造器) 变形1 : Xxx的静态方法 变形2 : XxBuilder/XxoxFactory的静态方法 2.Class的newInsta ...
- 深入理解java虚拟机(二)HotSpot Java对象创建,内存布局以及访问方式
内存中对象的创建.对象的结构以及访问方式. 一.对象的创建 在语言层面上,对象的创建只不过是一个new关键字而已,那么在虚拟机中又是一个怎样的过程呢? (一)判断类是否加载.虚拟机遇到一条new指令的 ...
- Java对象在虚拟机中的创建、内存分布、访问定位以及死亡判定
转载请注明原文地址:http://www.cnblogs.com/ygj0930/p/6535156.html 一:虚拟机中对象的创建 1:虚拟机遇到new指令时,在常量池检索是否有对应的符号引用, ...
随机推荐
- Statement和PreparedStatement的异同
1.首先两个都是java向数据库执行sql语句的对象! java代码连接数据库,并且执行sql语句的步骤如下: //1.注册数据库的驱动程序 Class.forName(driverClass); / ...
- codeforces 735C Tennis Championship(贪心+递推)
Tennis Championship 题目链接:http://codeforces.com/problemset/problem/735/C ——每天在线,欢迎留言谈论. 题目大意: 给你一个 n ...
- perfect-scrollbar在vue中的使用
1.下载perfect-scrollbar依赖包 npm install perfect-scrollbar 2.perfect-scrollbar特性 1)直接下载依赖包及包含css样式和js 2) ...
- A Java Runtime Environment (JRE) or Java Development Kit (JDK) must be available in order to run Eclipse. No Java virtual machine was found after searching the following locations: /usr/local/eclipse/
linux系统下jdk是已经安装好的情况之下软件出现 A Java Runtime Environment (JRE) or Java Development Kit (JDK) must be av ...
- MySQL 5.7安装指南
1.下载 1)进入官网下载5.7.23压缩包 下载地址:https://dev.mysql.com/downloads/mysql/5.7.html#downloads 2.安装与配置 1)将下载的压 ...
- 【公众号系列】SAP S/4 HANA 1809请查收
公众号:SAP Technical 本文作者:matinal 原文出处:http://www.cnblogs.com/SAPmatinal/ 原文链接:[公众号系列]SAP S/4 HANA 1809 ...
- EOS智能合约开发(一):EOS环境搭建和启动节点
EOS和以太坊很像,EOS很明确的说明它就是一个区块链的操作系统,BM在博客中也是说过的. 可以这样比喻,EOS就相当于内置激励系统的Windows/Linux/MacOS,这是它的一个定位. 包括以 ...
- adb错误处理
C:\Users\****\source\****>adb connect 192.168.10.* adb server version () doesn't match this clien ...
- Linux唤醒抢占----Linux进程的管理与调度(二十三)
1. 唤醒抢占 当在try_to_wake_up/wake_up_process和wake_up_new_task中唤醒进程时, 内核使用全局check_preempt_curr看看是否进程可以抢占当 ...
- 将正在运行的Proxmox EV5.x版本更新到最新版本
问题描述: 最近搭建了一个KVM开源虚拟化平台 Proxmox Virtual Environment是一种基于QEMU / KVM和LXC的开源服务器虚拟化管理解决方案.您可以使用集成的,易于使用的 ...