前往小程序,Get更优阅读体验!
立即前往
首页
学习
活动
专区
圈层
工具
发布
首页
学习
活动
专区
圈层
工具
MCP广场
社区首页 >专栏 >【Java】How Java Memory Works

【Java】How Java Memory Works

作者头像
阿东
发布于 2023-09-14 07:47:02
发布于 2023-09-14 07:47:02
13200
代码可运行
举报
运行总次数:0
代码可运行

Part1Source

How Java Memory Works?. Before we move on to the performence… | by Berkay Haberal | Jul, 2023 | Stackademic (medium.com)

Before we move on to the performence things, we need to learn that what is really going on in the background of JVM (Java Virtual Machine).

在开始讨论性能问题之前,我们需要了解 JVM(Java 虚拟机)的后台到底发生了什么。

This is the starting point of every developer who wants to learn and tune performance in order to gain some speed. So let’s dive into the world of codes.

这是每一个想要学习和调整性能以提高速度的开发人员的起点。因此,让我们进入代码的世界。

In Java, memory management is handled by JVM automatically to store your variables, classes, fields and beyond… The first thing we will learn is in JVM, memory splitted into two regions.

在 Java 中,内存管理由 JVM 自动处理,用于存储变量、类、字段和其他内容......我们首先要了解的是,在 JVM 中,内存分为两个区域。

One of them is called Stack and the other one is Heap.

其中一个称为堆(Stack),另一个称为堆(Heap)。

image.png

Part2What is Stack? 什么是堆栈?

First region we are going to learn is Stack.

我们要学习的第一个区域是

In JVM, stack is very efficent approach to memory management and not only just one but also every thread has its own stack region.

在 JVM 中,堆栈是一种非常有效的内存管理方法,不仅是一个线程,每个线程都有自己的堆栈区域。

In stack, instantiated fieds are added to memory one on another just like its name stacking.

在堆栈中,实例化的文件一个接一个地添加到内存中,就像堆栈的名字一样。

As you can see, this area is not big enough to store objects so what is happening is primitive types and object pointers can be stored directly instead of storing a whole object.

正如你所看到的,这个区域不够大,无法存储对象,因此可以直接存储原始类型对象指针,而不是存储整个对象。

1_MyD7U4_HzsZgMVLBSj068A.gif

And when it is time to remove, first object needs to be removed first because like I said, data is stacked, we can’t reach the bottom unless we remove those items.

当需要删除时,需要先删除第一个对象,因为就像我说的,数据是堆叠在一起的,如果不删除这些项目,我们就无法到达底部。

1_M6OarLjW8RJdLiQlTK3Jqw.gif

Part3What is Heap? 什么是堆?

Now, let’s look at the other region called Heap.

现在,让我们来看看另一个名为的区域。

As you can see it from the GIF, heap size is bigger than stack because heap is the main region for holding objects.

从 GIF 中可以看到,堆的大小大于栈,因为堆是存放对象的主要区域。

Every created object is held in heap and its reference is helding in stack.

每个创建的对象都存放在堆中,其引用存放在栈中。

Like figure shown below

如下图所示

代码语言:javascript
代码运行次数:0
运行
AI代码解释
复制
 public List<String> test() {  
    String newString = "test";  
    List<String> testList = new ArrayList<>();  
    testList.add(newString);  
    return testList;  
  }

On the contrary, there is just one heap that application has.

相反,应用程序只有一个堆。

That sounds quite reasonable because we might have more than one big object that passes one method to another.

这听起来很合理,因为我们可能有不止一个大对象,这些对象会将一个方法传递给另一个方法。

So basically, stack is used for local variables and there could be many stacks but they all use one heap to store the objetcs.

因此,堆栈基本上是用于局部变量的,可能有很多堆栈,但它们都使用一个堆来存储对象。

Those objects pointers are held in stack so when we want to pass objects between methods, we are not copying objects like in stack, we are passing its reference.

这些对象的指针保存在堆栈中,因此当我们要在不同方法之间传递对象时,我们不是像在堆栈中那样复制对象,而是传递其引用。

Furthermore, heap is not one, solid region at all. If you zoom in to the heap, you will see 4 different areas

此外,堆根本不是一个完整的区域。如果放大堆,你会看到 4 个不同的区域

image.png

Actually those are called generations. Heap is builded on two main generations. One of them is young and the other one is old. Young generation is divided into three spaces. Eden, survivor zero and survivor one spaces. It will be more clear when you learn what they do. Created objects are first placed in eden space. Then eden is fulled, objects are moved to the survivor one or survivor zero. After, created objects are placed in eden again. When eden is full, both eden and survivor zero or one will be moved to the survivor zero or one. If objects are moved more than five, those objects are now placed in old generation. This means, now those objects are needed and will live in old generation unless it looses its pointer. If there are no variables in the stack that holds its reference, this means that object is eligible for garbage collection. Last one is so important for performance issues and thus we need to learn how Java memory works to understand it.

实际上,这就是所谓的 "代"。堆建立在两个主代上。一个是Young,另一个是Old。Young代分为三个空间。Edensurvivor0survivor1

当你了解了它们的作用后就会更清楚了,新创建的对象首先被放置在Eden。

然后Eden被填满,存活对象被移动到survivor1survivor0。处理之后,后续创建的对象会再次放置在Eden中。

如果移动的对象超过 5 次,这些对象就会被放置在Old中。

这意味着,现在这些对象都是需要的,除非失去指针,否则它们都将留在Old中。

如果堆栈中没有任何对象引用,这意味着该对象符合垃圾回收的条件。

最后一条对于性能问题非常重要,因此我们需要学习 Java 内存的工作原理以便理解它。

Part4One more room for Metaspace please! 请为 Metaspace 多留一个位置!

Besides these regions, there is one more region in memory I want to mention. ==Metaspace is the region where application’s metadata is stored.==

除了这些区域外,我还想提到内存中的另一个区域:==元空间(Metaspace):是存储应用程序元数据的区域。==

Most of the times, we don’t need to know what is going on in metaspace due to its mission.

大多数时候我们并不需要知道元空间中发生了什么。

And there is one more mission it has and that is holding static variables, methods and classes in it.

但它还有一个使命,那就是保存静态变量、方法和类

This is why static keyword is accessable from anywhere because they are helding in metaspace so every thread can reach it easily.

这也是为什么静态关键字可以从任何地方访问,因为它们保存在元空间中,所以每个线程都可以轻松访问。

Part5Can we tune this size? 我们能调整这个尺寸吗?

Absolutely. There are flags we can use that tells JVM what to do when we are starting the application. We can some of these flags

当然可以。我们可以使用一些标记来告诉 JVM 在启动应用程序时要做什么。我们可以使用其中一些标志:

  • -XmsNg to set initial size
  • -XmxNg to set maximum size
  • -XX:NewRatio=N ratio of the young generation to the old generation
  • -XX:NewSize=N initial size of the young generariton
  • -XX:MaxNewSize=N maximum size of the young generation

-XmsNg :用于设置初始大小。-XmxNg :用于设置最大大小。-XX:NewRatio=N新生代与老年代的 N 比值-XX:NewSize=N新生代初始大小-XX:MaxNewSize=N:年轻代的最大尺寸

And we’ve reached our deadline. Before we move onto the Garbage Collection, it was essential to learn how Java memory works to have a better understanding about Garbage Collection. I hope I see you in my next article. Happy Coding!

在学习垃圾回收之前,我们有必要了解一下 Java 内存的工作原理,以便更好地理解垃圾回收。希望我们在下一篇文章中再见。编码快乐

本文参与 腾讯云自媒体同步曝光计划,分享自微信公众号。
,如有侵权请联系 cloudcommunity@tencent.com 删除

本文分享自 微信公众号,前往查看

如有侵权,请联系 cloudcommunity@tencent.com 删除。

本文参与 腾讯云自媒体同步曝光计划  ,欢迎热爱写作的你一起参与!

评论
登录后参与评论
暂无评论
推荐阅读
编辑精选文章
换一批
面试官:说说JVM内存整体结构?
Java 虚拟机定义了若干种程序运行期间会使用到的运行时数据区,其中有一些会随着虚拟机启动而创建,随着虚拟机退出而销毁。另外一些则是与线程一一对应的,这些与线程一一对应的数据区域会随着线程开始和结束而创建和销毁。
鲁大猿
2024/01/04
2440
面试官:说说JVM内存整体结构?
java:线上问题排查常用手段
然后执行 jmap -histo:live 7320 (注:如果输出内容太多,只想看排名前10的,可以加 | head -10)
菩提树下的杨过
2018/09/20
8340
java:线上问题排查常用手段
【Java】Java - GC 是如何工作的
Java — How GC works. One of the most notable features of… | by RR | Jul, 2023 | Medium
阿东
2024/05/08
1760
【Java】Java - GC 是如何工作的
JVM堆外内存问题排查
JVM 堆内存一般分析的比较多,本篇谈谈堆外内存问题排查,通常我们需要排查堆外内存的原因是系统整个内存使用飙高,但是堆内内存使用正常。这时候就需要分析堆外内存了
方丈的寺院
2019/08/05
5.8K0
「周一电台 x 训练营」从三道题开始,认识Java内存
几乎所有的对象实例以及数组在堆里分配内存。Java堆还是垃圾收集器(Garbage Collection,GC)管理的主要区域,因此我们也可以叫它GC堆,请勿叫做垃圾堆!
翊君
2022/03/15
3040
「周一电台 x 训练营」从三道题开始,认识Java内存
JVM 面试深入理解内存模型和垃圾回收(二)
https://docs.oracle.com/javase/specs/jvms/se8/html/jvms-2.html#jvms-2.5 >>>
架构探险之道
2023/03/04
4660
JVM 面试深入理解内存模型和垃圾回收(二)
深入浅出java虚拟机系列:(一)jvm 内存区域
java与c++之间有一堵由动态内存分配和垃圾收集技术所谓成的“高墙”,墙外面的人想进去,墙里面的人却想出来。
爱笑的架构师
2020/09/24
2570
深入浅出java虚拟机系列:(一)jvm 内存区域
JVM知识学习与巩固
JVM是Java Virtual Machine(Java虚拟机)的缩写,JVM是一种用于计算设备的规范,它是一个虚构出来的计算机,是通过在实际的计算机上仿真模拟各种计算机功能来实现的。
用户3003813
2018/09/06
5100
JVM知识学习与巩固
jvm系列(四):jvm调优-命令篇
运用jvm自带的命令可以方便的在生产监控和打印堆栈的日志信息帮忙我们来定位问题!虽然jvm调优成熟的工具已经有很多:jconsole、大名鼎鼎的VisualVM,IBM的Memory Analyzer等等,但是在生产环境出现问题的时候,一方面工具的使用会有所限制,另一方面喜欢装X的我们,总喜欢在出现问题的时候在终端输入一些命令来解决。所有的工具几乎都是依赖于jdk的接口和底层的这些命令,研究这些命令的使用也让我们更能了解jvm构成和特性。 Sun JDK监控和故障处理命令有jps jstat jmap jh
纯洁的微笑
2018/04/19
1.9K0
jvm系列(四):jvm调优-命令篇
Java 内存模型之堆内存(Heap)
1、什么是 Perm Gen? Perm Gen : Permanent Generation  Perm Gen 区是一个特殊的JVM内存区,因为它用来存储用来描述 Class 的  元数据(Class 可以不属于Java语言的一部分,也可以属于),诸如:描述类及其方法。  在大的应用中该区一会儿就满了,并抛出错误:java.lang.OutOfMemoryError: PermGen  然而无论你怎么设置 -Xmx 也不管用。  因为设置其大小的参数不是 -Xmx,而是 -XX:PermGen, -XX:MaxPermGen (不同Java版本略有变化)  2、Heap VS. Stack VS. Perm Heap(堆内存):  使用Java语言创建的所有的引用对象类型,都在此存储。并由 GC (Garbage Collection)对其进行管理,  诸如:释放不再被程序引用的对象所占据的内存。  Stack(栈内存):  与 Heap 相对的是,Stack 存放基础数据类型。诸如:int, char 等。  由程序的执行顺序控制变量的进出栈顺序,而不是由 GC 控制栈内存的管理。  Perm(持久内存):  用于存储类的元数据。诸如:类的定义,方法的定义等。  Perm 的生命周期与 JVM 绑定,而 Heap 的生命周期与程序绑定。  二、堆内存(Heap) 与 Garbage Collection 理解 GC (Garbage Collection),需要理解 Heap 。  JVM 的 Heap 堆内存在物理上被划分为两部分:Young Gen, Old Gen  1、 JVM 内存管理之:Young Gen 所有新创建的 Object 首先被放在 Young Generation 内存区。  如果 Young Generation 内存区满了,则执行 Garbage Collection 。这种 GC 称为 Minor GC。  Young Generation 区又分为三部分: Eden Memory,Survivor0 Memory (S0),Survivor1 Memory(S1).  Young Generation 内存区要点:  1、绝大多数新建的 Object 被放在 Eden Memory  2、如果 Eden Memory 内存满了,则进行 GC 操作。     同时把未被 GC 的 Object 移动到 S0 或 S1 中。     此时 Minor GC 也会检查和移动 S0 和 S1 中的对象。     最后使 S0,S1 其中一个置为空。  3、多次 GC 后仍然未被 GC 的 Object 将被移动到 Old Gen 内存区中。     通常 Object 会被 GC 设定一个轮询的阀值。  2、 JVM 内存管理之:Old Gen Old Gen 内存区存放了经过多次 Minor GC 后仍然不能被 GC 的 Object。  与 Young Gen 相同,当 Old Gen 区满了之后将执行 GC 操作,该操作称为:Major GC。  耗用的时间也相对较长。  stop-the-world 事件  Young Gen 和 Old Gen 都可以主动触发 stop-the-world 事件,挂起所有任务,执行 GC 操作。  被挂起的任务只有在 GC 执行完毕后,才会恢复执行。  多数情况下, GC 性能调优(GC tuning)就是指降低 stop-the-world 时 GC 执行的时间。  三、Perm Gen  JVM 在 Permanent Generation 或 Perm Gen 内存区中存放应用程序的元数据  (application metadata),用来描述类及其方法的原始信息。  注意:Perm Gen 不是 Heap 的一部分。  Perm Gen 被 JVM 使用于应用程序运行期间(runtime),基于应用所使用到的类。  Perm Gen 中同时包括 Java SE 包中的类。  Perm Gen 只有在执行 Full GC 时才会被 GC。  四、内存管理调优参数 -Xms  设置JVM启动时的堆内存(Heap)的大小  -Xmx For setting the maximum heap size.  设置堆内存(Heap)的最大值  -Xmn  设置 Young Gen 内存区的大小  -XX:PermGen  设置 Perm Gen 内存的初始大小  -XX:MaxPermGen  设置 Perm Gen 内存的最大值  -XX:SurvivorRatio  设置 Eden Gen 与 S0 Gen,S1 Gen 内存的大小比。默认值:8  例如:  Yo
凯哥Java
2022/12/15
5500
Java 内存模型之堆内存(Heap)
java9系列(九)Make G1 the Default Garbage Collector
本文主要研究下JEP 248: Make G1 the Default Garbage Collector
code4it
2018/09/17
8330
java 资深程序员第一课;jvm优化、了解jvm运行加载class变量过程
        1、首先运行程序,Demo1_car.java就会变为Demo1_car.class,将Demo1_car.class加入方法区,检查是否字节码文件常量池中是否有常量值,如果有,那么就加入运行时常量池
冯杰宁
2019/07/01
6010
java 资深程序员第一课;jvm优化、了解jvm运行加载class变量过程
频繁GC (Allocation Failure)及young gc时间过长分析
本文主要分析一个频繁GC (Allocation Failure)及young gc时间过长的case。
code4it
2018/09/17
13.2K0
java内存分配和String类型的深度解析
在java语言的所有数据类型中,String类型是比较特殊的一种类型,同时也是面试的时候经常被问到的一个知识点,本文结合java内存分配深度分析关于String的许多令人迷惑的问题。下面是本文将要涉及到的一些问题,如果读者对这些问题都了如指掌,则可忽略此文。
哲洛不闹
2018/09/19
7680
java内存分配和String类型的深度解析
JVM内存管理
Java内存管理是一项持续的挑战,同时也是锻造出可拓展应用的必备技能。本质上,Java内存管理就是一个为新对象分配内存和释放无用对象内存的过程。
码代码的陈同学
2018/06/03
2.3K0
JVM内存管理
原 荐 JVM笔记整理
不对之处还望指正。 垃圾回收 1. 如何判断对象是垃圾对象? 引用计数法 在对象中添加一个引用计数器,当有地方引用这个对象的时候,引用计数器的值+1,当引用失效时,则值-1. 此方式不能解决循环引用
石奈子
2018/06/13
5790
java(9)-深入浅出GC垃圾回收机制
1、本文了解GC垃圾回收机制,深入理解GC后才明白,为啥FGC会导致stop-the-world。 2、了解GC算法。
黄规速
2022/04/14
1K0
java(9)-深入浅出GC垃圾回收机制
干货 | 一文看懂JVM内存布局及GC原理
杨俊明,携程云客服平台研发部软件技术专家。从事IT行业10余年,腾讯云+社区、阿里云栖社区、华为云社区认证专家。近年来主要研究分布式架构、微服务、java技术等方向。
携程技术
2019/08/29
1.2K0
干货 | 一文看懂JVM内存布局及GC原理
jvm系列--GC
一般情况下,当新对象生成,并且在Eden申请空间失败时,就会触发Scavenge GC,对Eden区域进行GC,清除非存活对象,并且把尚且存活的对象移动到Survivor区。
Dlimeng
2023/06/29
1930
jvm系列--GC
JVM架构和GC垃圾回收机制(JVM面试不用愁)[通俗易懂]
JVM全称是Java Virtual Machine(Java虚拟机),Java虚拟机是一种程序虚拟机(相对操作系统虚拟机),Java的运行环境实现跨平台。
全栈程序员站长
2022/08/11
4260
JVM架构和GC垃圾回收机制(JVM面试不用愁)[通俗易懂]
相关推荐
面试官:说说JVM内存整体结构?
更多 >
领券
问题归档专栏文章快讯文章归档关键词归档开发者手册归档开发者手册 Section 归档
本文部分代码块支持一键运行,欢迎体验
本文部分代码块支持一键运行,欢迎体验