jvm专题 之 内存模型

news2024/9/29 15:25:02

文章目录

  • 前言
  • 一个java对象的运行过程
  • jvm内存分布
  • 程序的基本运行程序
    • 对象
      • 什么是对象
      • 对象的创建
        • 一、类加载检查
        • 二、对象内存分配
        • 三、初始化零值
        • 四、设置对象头
        • 五、执行初始化方法
      • 对象的访问定位
    • 对象与类的关系
    • 由类创建对象的顺序
  • 对象的创建

前言

  • 一个程序需要运行,需要在内存中开辟一块空间
  • 类是构建对象的模板,只有类加载到内存中才能创建对象

一个java对象的运行过程

在这里插入图片描述

1、我们自己创建一个Test类,功能只有一个:System.out.println(“hello world”);
2、然后通过终端运行 javac Test.java,会将Test类编译成二进制字节码文件Test.class
3、然后我们继续运行 java Test.class,于是会打印出“hello world”。
4、控制着程序的执行流程的是虚拟机栈
( 打印的过程就是在内存中进行的)

jvm内存分布

  • 由上边图可以看到,jvm主要分为五个区域。我们可以分为两大类:

    线程独享:程序计数器、本地方法栈、虚拟机栈
    线程共享:堆、方法区

  • 每个区域主要的职责,参看上图就可以了,这里不多数
    (各位读者,如果有了解本地方法栈的,欢迎留言哦)

程序的基本运行程序

在java中,万物皆可对象。那么,什么是对象呢,对象与类又是什么关系呢?

对象

什么是对象

  • 对象是堆内的一块内存空间,是由类构建出来的

对象的创建

一、类加载检查
  • 检查 能否在常量池中定位到一个类的符号引用,并检查这个符号引用代表的类是否被加载、解析和初始化
    • 如果类已经加载过了,会在方法区有一个类的class对象
    • 如果类没有加载过,需要先执行类的加载流程
二、对象内存分配
  • 类加载检查通过 后,接下来虚拟机为新生对象分配内存(大小在类加载完成后便可以完全确定)

    • 分配内存的方法
      • 指针碰撞法(假设java中内存是绝对规整的)(带Compact的收集器,如Serial ParkNew)
      • 空闲列表法(java堆中内存并不规整)(基于Mark-Sweep算法的收集器,如CMS)
    • 多线程时如何保证划分的空间可用?

      (1) 使用CAS配上失败重试的方式保证更新操作的原子性
      (2)本地线程分配缓冲TLAB:线程开启时,虚拟机为每个线程分配一块较大的空间,然后线程内部创建对象时从自己的空间分配
      (每个线程在java堆中预先分配内存TLAB,可以通过-XX:+/-UseTLAB参数来设定)

三、初始化零值

给实例对象的成员变量赋零值,如int型为0,引用类型为null。
这样在没有赋值的情况下,对象也可以使用

四、设置对象头
  • 对象头
    • Mark Word:HashCode、GC分代年龄、持有锁的状态、偏向线程ID、偏向时间戳
    • 类型指针:指向类元数据的指针(虚拟机通过这个指针来确定这个对象时哪个类的实例)
  • 实例数据:对象真正存储的有效信息(相同的宽度总是被分配到一起)
  • 对齐填充:jvm要求对象的大小必须是8字节的整数倍
五、执行初始化方法

如 构造方法

对象的访问定位

  • 直接指针:对象实例数据 + 对象类型数据的指针
    • 特点:java堆中存储 对象实例数据+对象类型数据的指针 放在一起
    • 优点:访问速度快
  • 句柄指针:(句柄池中)对象实例数据的指针 + 对象类型数据的指针;对象实例数据在堆中额外的位置
    • 特点:java堆中需要划分出一部分来作为句柄池,
    • 好处:有稳定的句柄池,在对象被移动时只会改变句柄池中的指针
    • 缺点:相比直接指针,访问速度慢

对象与类的关系

  • 类是构建对象的模板,类中有什么,对象当中有什么。

由类创建对象的顺序

  • 我们先来一个Person类,然后再来一个Test类用来测试,一起来看一下顺序

  • 代码

    public class Person {
        String name;
        Integer age;
        Character sex;
        public static void breath(){
            System.out.println("会呼吸");
        }
        public void speek(){
            System.out.println("可以说话");
        }
    }
    
    public class Test {
        public static void main(String[] args) {
            Person person1 = new Person();
            person1.name = "Lucy";
            person1.age = 20;
            person1.sex = 'F';
            System.out.println(person1.name+",年龄为:"+person1.age+",性别是:"+person1.sex);
            person1.breath();    // 也可以Person.breath();
            person1.speek();
            
            // person2是为了后续的内容讲解,此处先不用关注
            Person person2 = new Person();
            person2.name = "Lucy";
            person2.age = 20;
            person2.sex = 'F';
            person2.breath();
            person2.speek();
        }
    }
    

    备注:person2是为了对比,下边内容讲解会先忽略这里,只看person1

  • 内存图
    在这里插入图片描述

    执行顺序:
    1、加载Test类信息到方法区中
    2、main()方法入栈
    3、加载Person类信息到方法区
    4、给对象person1的name赋值,name为String类型,person1对象中name指向的是一个引用地址,数据存放在方法区的字符串常量池中
    5、给对象person1的age赋值,age为Integer类型,当age取值为[-128,127]时,age指向的是数组中的某一个。如果超出范围,会创建新的Integer对象
    6、给对象的sex赋值,在堆中创建一个对象
    7、调用breath()方法
    8、调用speek()方法

  • 多说两句(以上边的person1和person2来比对)

    • 如果age取值在[-128,127]内,多个对象指向的是同一内存空间
      System.out.println(person1.age == person2.age);
      -------------
      true
      
    • 如果age取值不在[-128,127]之间,那么不同的对象的age需要在堆中额外创建对象
      person1.age = 200;
      person2.age = 200;
      System.out.println(person1.age == person2.age);
      --------运行结果---------
      false
      
    • 对于Character类,只要值相等,那么多个对象指向的是同一空间地址
      System.out.println(person1.sex == person2.sex);
      --------运行结果---------
      true
      

对象的创建

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

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

相关文章

编程语言图书创作要注意的事情有哪些?

编程语言图书的创作是一项复杂且具有挑战性的任务,需要作者深入理解技术、清晰表达,并考虑读者的学习体验。一本优秀的编程书籍不仅能够教授技术知识,更能引导读者逐步深入,激发他们的思考和实际应用能力。以下将详细探讨编程语言…

Python库matplotlib之三

Python库matplotlib之三 小部件(widget)小部件的基类connect_eventdisconnect_events() Buttondisconnecton_clicked应用实列 CheckButtons构造器APIs应用实列 小部件(widget) 小部件(widget)可与任何GUI后端一起工作。所有这些小部件都要求预定义一个Axes实例,并将…

ASP.NET Core 创建使用异步队列

示例图 在 ASP.NET Core 应用程序中,执行耗时任务而不阻塞线程的一种有效方法是使用异步队列。在本文中,我们将探讨如何使用 .NET Core 和 C# 创建队列结构以及如何使用此队列异步执行操作。 步骤 1:创建 EmailMessage 类 首先&#xff0c…

工作繁杂,如何防止工作遗漏遗忘?

不知道大家工作中是否有这样的情况: 1.工作过程中工作任务经常被打断,打乱正常的工作节奏; 2.因为不方便统一记录工作及工作要求,经常忘记给领导反馈工作进展; 3.因为工作繁多,经常会出现工作遗漏遗忘的…

ass字幕文件怎么导入视频mp4?ass字幕怎么编辑?视频加字幕超简单!

ass字幕文件怎么导入视频mp4?ass字幕怎么编辑?在视频制作和观看过程中,添加字幕是一项常见的需求,特别是对于外语视频或需要辅助阅读的场景。ASS(Advanced SubStation Alpha)字幕文件是一种常用的字幕格式&…

Redission · 可重入锁(Reentrant Lock)

前言 Redisson是一个强大的分布式Java对象和服务库,专为简化在分布式环境中的Java开发而设计。通过Redisson,开发人员可以轻松地在分布式系统中共享数据、实现分布式锁、创建分布式对象,并处理各种分布式场景的挑战。 Redisson的设计灵感来…

华为OD机试 - 静态扫描(Java 2024 E卷 100分)

华为OD机试 2024E卷题库疯狂收录中,刷题点这里 专栏导读 本专栏收录于《华为OD机试(JAVA)真题(E卷D卷A卷B卷C卷)》。 刷的越多,抽中的概率越大,私信哪吒,备注华为OD,加…

八LAMP搭建

# LAMP ## 一、知识回顾 ### FTP samba nfs 特点 - 借用Linux用户作为映射用户,进行权限管理 - 软件本身还有管理控制权限 #### 客户端连接到服务器后进行读写执行等操作 ,必须同时具有: - 软件许可的权限 vsftpd: anon upload enableYES - 文件…

PC端微信小程序如何调试?

向往常一样运行开微信小程序开发者工具 如果只弹出pc端小程序,没有出现调试的界面:点击胶囊按钮的三个…选择重新进入小程序 即可依次展开相应的功能调试,改完代码没反应再刷新看看,再没反应就再次重新点击编译并自动调试。

fish-speech语音大模型本地部署

文章目录 fish-speech模型下载编译部署 小结 fish-speech模型 先说下fish-speech模型吧,可以先看下官网。如下: 这就是一个模型,可以根据一个样例声音,构建出自己需要的声音。其实,这个还是有很多用途的;…

Tpflow:提升开发效率的PHP工作流引擎

Tpflow:提升开发效率的PHP工作流引擎 今天要跟大家介绍的是一款能够显著提升开发效率的工具——Tpflow!它是一个专门为PHP开发者设计的工作流引擎,致力于帮助你减少80%以上的代码量,轻松管理复杂的业务流程。让我们一起来看看它的…

win10安装Java闪退

问题:win10 在安装Java8时,电脑没有反应,出现闪退的现象。 1、打开设置找到“时间和语言” 2、找到“中文(简体,中国)” 3、点击“选项” 4、删除“百度输入法” 5、问题解决,再次安装Java

史上最细快速排序讲解(hoare,挖坑,双指针, 非递归)

文章目录 前言一、递归方法快排1. 递归主要思想2. 递归代码实现 二、hoare方法实现找基准值1. hoare思想2. hoare代码实现 三、挖坑方法实现找基准值1. 挖坑思想2. 挖坑代码实现 四、双指针方法实现找基准值1. lomuto前后指针法思想2. lomuto前后指针法代码实现 五、非递归方法…

第十四周:机器学习笔记

第十四周周报 摘要Abstract一、机器学习——Transformer(下)1. Transformer decoder1.1 autoregressive decoder(自回归解码器)1.2 Transformer decoder结构图1.3 non-autoregressive decoder(非自回归解码器&#xff…

24年最新 idea 插件开发教程,面试鸭插件技术实现!

大家好,我是松柏。今天给大家分享下这个JetBrains插件开发教程。 学习过程中可以参考开源项目:https://github.com/yuyuanweb/mianshiya-plugin 首先贴一下官方文档:https://plugins.jetbrains.com/docs/intellij/welcome.html 虽然这个文档…

【最新发布】Win10 22H2 19045.4957 正式版免费下载!

今日系统之家小编给大家分享2024年9月第二次更新的Windows10 22H2正式版系统,该版本系统基于最新Windows10 22H2 19045.4957 64位专业版进行离线制作,安全无毒,修复了使用某些环绕声技术时某些媒体的播放可能会停止等多项问题,系统…

基于C#开发的(CS界面)图书管理系统

图书管理系统项目开发说明书 项目简介 项目背景(选择这个项目的原因、前景,面向的用户,优势); 根据温州理工学院需要希望能够充分利用现代科技来提高图书管理的效率,在原有的办公系统基础上进行扩展&…

1. 如何在服务器上租GPU跑实验 (以AutoDL为例) - 深度学习·科研实践·从0到1

目录 前言 1. 在AutoDL上注册账号 2. 在算力市场选择GPU 3. 创建实例 4. 控制台-容器实例界面(核心) 4.1 无卡模式(常用) 5. 帮助文档 前言 好记性不如烂笔头,本专栏将详细记录下本人学习深度学习工程实践&…

Python通过Sqlalchemy框架实现增删改查

目录 简介 什么是SQLAlchemy? SQLAlchemy可以分为两个部分:Core和ORM。 一、首先安装sqlalchemy 二、在配置文件中添加数据库连接信息,我这里是Mysql 三、 创建数据库连接类,我这里是动态读取数据库的表字段,自动…