【JVM】对象实例化内存布局与访问定位

news2024/9/23 13:29:41

对象实例化

面试题

美团:
对象在JVM中是怎么存储的?
对象头信息里面有哪些东西?
蚂蚁金服:
Java对象头有什么?
在这里插入图片描述

对象创建方式

  • new:最常见的方式、单例类中调用getInstance的静态类方法,XXXFactory的静态方法
  • Class的newInstance方法:在JDK9里面被标记为过时的方法,因为只能调用空参构造器
  • Constructor的newInstance(XXX):反射的方式,可以调用空参的,或者带参的构造器
  • 使用clone():不调用任何的构造器,要求当前的类需要实现Cloneable接口中的clone接口
  • 使用序列化:序列化一般用于Socket的网络传输
  • 第三方库 Objenesis

创建对象的步骤

判断对象对应的类是否加载、链接、初始化

虚拟机遇到一条new指令,首先去检查这个指令的参数能否在Metaspace的常量池中定位到一个类的符号引用,并且检查这个符号引用代表的类是否已经被加载,解析和初始化。(即判断类元信息是否存在)。如果没有,那么在双亲委派模式下,使用当前类加载器以ClassLoader + 包名 + 类名为key进行查找对应的 .class文件,如果没有找到文件,则抛出ClassNotFoundException异常,如果找到,则进行类加载,并生成对应的Class对象。

为对象分配内存

首先计算对象占用空间的大小,接着在堆中划分一块内存给新对象。如果实例成员变量是引用变量,仅分配引用变量空间即可,即4个字节大小

  • 如果内存规整:指针碰撞
    • 如果内存是规整的,那么虚拟机将采用的是指针碰撞法(Bump The Point)来为对象分配内存。
      意思是所有用过的内存在一边,空闲的内存放另外一边,中间放着一个指针作为分界点的指示器,分配内存就仅仅是把指针指向空闲那边挪动一段与对象大小相等的距离罢了。如果垃圾收集器选择的是Serial ,ParNew这种基于压缩算法的,虚拟机采用这种分配方式。一般使用带Compact(整理)过程的收集器时,使用指针碰撞。
  • 如果内存不规整
    • 虚拟表需要维护一个列表
    • 空闲列表分配
      如果内存不是规整的,已使用的内存和未使用的内存相互交错,那么虚拟机将采用的是空闲列表来为对象分配内存。意思是虚拟机维护了一个列表,记录上那些内存块是可用的,再分配的时候从列表中找到一块足够大的空间划分给对象实例,并更新列表上的内容。这种分配方式成为了 “空闲列表(Free List)”
  • 说明
    选择哪种分配方式由Java堆是否规整所决定,而Java堆是否规整又由所采用的垃圾收集器是否带有压缩整理功能决定。

处理并发问题

  • 采用CAS配上失败重试保证更新的原子性
  • 每个线程预先分配TLAB - 通过设置 -XX:+UseTLAB参数来设置(区域加锁机制)
    (在Eden区给每个线程分配一块区域)

初始化分配到的内存

给对象属性赋值的操作
属性的默认初始化
显示初始化
代码块中的初始化
构造器初始化
所有属性设置默认值,保证对象实例字段在不赋值可以直接使用

设置对象的对象头

将对象的所属类(即类的元数据信息)、对象的HashCode和对象的GC信息、锁信息等数据存储在对象的对象头中。这个过程的具体设置方式取决于JVM实现。

执行init方法进行初始化

在Java程序的视角看来,初始化才正式开始。初始化成员变量,执行实例化代码块,调用类的构造方法,并把堆内对象的首地址赋值给引用变量

因此一般来说(由字节码中跟随invokespecial指令所决定),new指令之后会接着就是执行方法,把对象按照程序员的意愿进行初始化,这样一个真正可用的对象才算完成创建出来。

对象实例化的过程

加载类元信息
为对象分配内存
处理并发问题
属性的默认初始化(零值初始化)
设置对象头信息
属性的显示初始化、代码块中初始化、构造器中初始化

对象内存布局

在这里插入图片描述

对象头

对象头包含了两部分,分别是 运行时元数据(Mark Word)和 类型指针
如果是数组,还需要记录数组的长度

运行时元数据

哈希值(HashCode)
GC分代年龄
锁状态标志
线程持有的锁
偏向线程ID
翩向时间戳

类型指针

指向类元数据InstanceKlass,确定该对象所属的类型。指向的其实是方法区中存放的类元信息

实例数据(Instance Data)
说明
不是必须的,也没有特别的含义,仅仅起到占位符的作用

小结

在这里插入图片描述

对象的访问定位

图示

JVM是如何通过栈帧中的对象引用访问到其内部的对象实例呢?
在这里插入图片描述

对象访问的两种方式

句柄访问

在这里插入图片描述
句柄访问就是说栈的局部变量表中,记录的对象的引用,然后在堆空间中开辟了一块空间,也就是句柄池

优点
reference中存储稳定句柄地址,对象被移动(垃圾收集时移动对象很普遍)时只会改变句柄中实例数据指针即可,reference本身不需要被修改

直接指针(HotSpot采用)

在这里插入图片描述
直接指针是局部变量表中的引用,直接指向堆中的实例,在对象实例中有类型指针,指向的是方法区中的对象类型数据

直接内存 Direct Memory

  • 不是虚拟机运行时数据区的一部分,也不是《Java虚拟机规范》中定义的内存区域。
  • 直接内存是在Java堆外的、直接向系统申请的内存区间。
  • 来源于NIO,通过存在堆中的DirectByteBuffer操作Native内存
  • 通常,访问直接内存的速度会优于Java堆。即读写性能高。(下面非直接缓存区和缓存区标题解释了这一点)
    • 因此出于性能考虑,读写频繁的场合可能会考虑使用直接内存。
    • Java的NIO库允许Java程序使用直接内存,用于数据缓冲区

使用下列代码,直接分配本地内存空间

int BUFFER = 1024*1024*1024; // 1GB
ByteBuffer byteBuffer = ByteBuffer.allocateDirect(BUFFER);

非直接缓存区和缓存区

原来采用BIO的架构,我们需要从用户态切换成内核态
在这里插入图片描述
NIO的方式使用了缓存区的概念

存在的问题

  • 也可能导致outofMemoryError异常
  • 由于直接内存在Java堆外,因此它的大小不会直接受限于-xmx指定的最大堆大小,但是系统内存是有限的,Java堆和直接内存的总和依然受限于操作系统能给出的最大内存。
  • 缺点
  • 分配回收成本较高
  • 不受JVM内存回收管理
  • 直接内存大小可以通过MaxDirectMemorySize设置
  • 如果不指定,默认与堆的最大值-xmx参数值一致
    在这里插入图片描述

本文来自互联网用户投稿,该文观点仅代表作者本人,不代表本站立场。本站仅提供信息存储空间服务,不拥有所有权,不承担相关法律责任。如若转载,请注明出处:http://www.coloradmin.cn/o/69006.html

如若内容造成侵权/违法违规/事实不符,请联系多彩编程网进行投诉反馈,一经查实,立即删除!

相关文章

spark技术特点

一、Hadoop是什么?Hadoop和Spark有什么区别 Hadoop是什么? Hadoop是一个开源的框架,可编写和运行分布式应用处理大规模数据,是专为离线和大规模数据分析而设计的,并不适合那种对几个记录随机读写的在线事务处理模式。HadoopHDFS&#xff0…

COHERENT VERDI 18w激光电源维修注意事项

主要功能: 该激光器可以进行皮秒、飞秒两种模式间的转换,为我们实现皮秒、飞秒级时间内的很快确定性激发提供了基础。同时激发激光需要有足够的功率,才能在少数甚至一个脉冲内确定性的将离子激发到激发态,按照计算选取了泵浦光18…

UAVDT数据集转化为MOT数据集(用作MOTR模型训练)

文章目录UAVDT数据集转化为MOT数据集MOT17 数据集格式traindet.txtgt.txtseqinfo.initestdet.txtUAVDT1. 自行创建下面文件夹路径2. 操作并得到gt.txtseqinfo.ini代码UAVDT数据集转化为MOT数据集 MOT17 数据集格式 ├── MOT17 │ ├── images │ ├── labels_with_…

人工智能期末考试

第一章-绪论 1. 人工智能的定义 定义:使机器的软件或程序,通过某些算法进行数据学习,并使用所学进行仿人决策。 2. 人工智能的各种认知观 符号主义(symbolism) 原理:基于物理符号系统假设和有限合理性原理,起源于数…

SoviChart数据可视化:燃尽图(Burn down chart)

在一个完美的世界里,敏捷项目中的每个Sprint都会完全按计划进行,用户将提供充足的时间表,项目的各个方面都将保持正轨。但是,在现实世界中,会出现范围变化和不可预见的问题,这可能会导致会议和项目时间表延…

Oracle数据表ID自增操作

1、SQL编写 -- 新建用户 create user root IDENTIFIED by 123456; -- 将默认的USERS空间分配给用户 alter user root default tablespace users; -- 授权角色以及权限(默认三个角色:connect、resource、dba) grant create session,create ta…

Java数据结构与Java算法学习Day07---优先队列(简略笔记记录)

目录 一、优先队列 106 1.1优先队列的概念 106 1.2最大优先队列API设计 107 1.3最小优先队列 109 1.3.1最小优先队列API设计 110 1.4索引优先队列 (添加两个数组解决该问题)112 1.4.1索引优先队列的原理 112 1.4.2 索引优先队列API设计 113 1…

Spark Windows10 安装

目录一、Scala的安装二、Spark的安装1、Spark的几个版本的意思2、Spark的最新版本:[Spark最新版](https://spark.apache.org/downloads.html)3、安装Spark4、下载winutils在我们安装Spark之前,由于Spark基于Scala的,所以我们需要先安装Scala。…

机床测头应用二:自动补偿功能,提升生产良率

机床测头仿形加工功能可以保证“第一件和第一百件尺寸一致”机床测头应用一:仿形加工功能,降低废品率,此外它的自动补偿功能,也是批量生产中不可缺少的重要质量控制手段。机床测头的自动补偿能实现加工前准确找到工件中心自动更新…

从零开始学习JMETER性能测试

从零开始学习JMETER性能测试 顶级 Jmeter 讲座通过实时示例解释负载测试,包括材料和查询支持 课程英文名:Learn JMETER from Scratch on Live Apps Performance Testing 此视频教程共17.0小时,中英双语字幕,画质清晰无水印&…

实战项目演练丨九哥带你搭建精美的博客后台管理系统!

本项目是一个博客后台管理系统,主要包含四个大模块:用户、分类、博客和评论。项目启动后需要通过管理员身份进入系统,进入系统后会呈现后台管理主界面,通过后左侧的导航菜单,实现不同模块的数据维护。 一. 基本简介 …

美食杰项目(七)菜谱大全

本文目录前言:1.具体样式2.实现的具体功能和代码思路3.element ui具体样式的网址4.相关代码5.总结:前言: 本文给大家讲的是美食杰项目中菜谱大全项目的具体样式,代码思路和具体代码,希望能帮助到你 1.具体样式 2.实现…

Zabbix6.0使用教程 (一)—zabbix新增功能介绍1

使用zabbix的小伙伴应该都有关注到目前zabbix的大版本已经更新到了6.0,后面乐乐将会对如何使用zabbix6.0做一个使用教程的系列,大家可以持续关注,这篇我们主要聊聊zabbix6.0新增的一些功能介绍。 一、Zabbix server 的高可用集群 新版本附带…

Hadoop Windows10 安裝

安裝Hadoop之前,我们先需要安装JDK,JDK的安装我就不多说了 一、安装JDK 1、到Oracle的官网中下载jdk,然后解压到一个指定的文件夹,如:D:\Program Files\Java\jdk-15.0.1 2、配置环境变量:在我的电脑中的高…

SCRM是什么,SCRM和CRM区别?

要想知道什么是SCRM?首先必须清楚SCRM和CRM的区别。 1、定义不同 CRM全称:Customer Relationship Management,中文叫“客户关系管理”,是指社会化客户关系管理。CRM一词流行至今已有20余年,是企业管理系统中专门针对客…

【MySQL】第01章_数据库概述

目录第01章_数据库概述1.为什么要使用数据库2.数据库与数据库管理系统2.1 数据库的相关概念2.2 数据库与数据库管理系统的关系3.MySQL介绍3.1 概述3.2 关于MySQL 8.04. RDBMS 与 非RDBMS4.1 关系型数据库(RDBMS)4.1.1 实质4.1.2 优势4.2 非关系型数据库(非RDBMS)4.2.1 介绍4.2.…

什么是JDBC?JDBC程序的具体实现步骤

什么是JDBC?JDBC程序的具体实现步骤JDBC的全称是Java数据库连接(Java Database Connectivity),它是一套用于执行SQL语句的Java API。应用程序可通过这套API连接到关系数据库,并使用SQL语句来完成对数据库中数据的查询、更新和删除等操作。应…

2-2-3-5-3、SynchronousQueue详解

简介 SynchronousQueue是一个没有数据缓冲的BlockingQueue,生产者线程对其的插入操作put必须等待消费者的移除操作take 如图所示,SynchronousQueue 最大的不同之处在于,它的容量为 0,所以没有一个地方来暂存元素,导…

排序算法-计数排序、桶排序、基数排序

计数排序、桶排序、基数排序 这三种排序算法都利用了桶的概念,都属于用空间换时间的算法。但对桶的使用方法上有明显差异: 计数排序:每个桶只存储单一键值;桶排序:每个桶存储一定范围的数值;基数排序&…

Linux网络基础(基础概念)

Linux网络基础(基础概念) 文章目录Linux网络基础(基础概念)1.计算机网络的发展过程1.1 独立模式1.2 网络互联模式1.3 局域网 LAN1.4 广域网 WAN2.计算机网络协议2.1 协议的概念2.2 什么是网络协议2.3 什么是网络协议簇2.4 OSI 七层模型2.5 TCP/IP 五层模型3.网络传输基本流程3.…