美文网首页
架构师训练营第9周作业 JVM垃圾回收 秒杀架构

架构师训练营第9周作业 JVM垃圾回收 秒杀架构

作者: 浩哥有料 | 来源:发表于2020-08-05 23:51 被阅读0次

请简述JVM垃圾回收原理

所谓垃圾回收,指的是JVM将堆空间中不再使用的对象清理掉的过程,这是由JVM自动完成的。根据JVM的架构,在启动JVM的时候会开辟一块内存空间作为堆空间,这个空间被JVM中的所有线程共享,Java程序运行中所有新创建的对象都会被放入堆空间。如由于堆空间的容量是有限的,如果不断的新建对象放入堆空间,那么很快空间就会不够用,因此必须对垃圾对象所占用的内存空间进行清理,回收可用的内存空间给后续的对象创建使用。

JVM的垃圾回收原理大致分为四个方面,分别是垃圾对象的识别、内存清理方法、分代回收以及垃圾回收器。

垃圾对象识别

JVM识别垃圾对象使用一种可达性分析算法,这个算法从线程栈中的局部变量和方法区中的静态变量出发,找到它们所引用的对象,并递归地查找这些对象是否还有引用其他对象,对所有引用到的对象进行标记,直到没有更多对象可以标记。那么所有被标记过的对象就是仍在使用的对象,而剩下的未标记的对象则是可回收的垃圾对象。

内存清理方法

在标记完存活对象之后,对于垃圾对象所占用的内存空间即可执行清理。最简单的方式就是直接清空这些内存空间,而在实际操作中,只需把这些内存空间的状态改为空闲,这样如果有新对象创建需要分配内存空间,只需从这些空闲空间中进行分配即可,这跟硬盘删除文件时的原理是类似的。但是,如果只是简单地清理这些垃圾对象占用的内存空间,会导致这些被回收的空间分布零散、不连续,这样如果有较大的对象需要创建的话,小空间就无法被用上。因此第二种方法是将存活对象统一移动到一段连续的内存空间,而剩下的连续空间则都是空闲的,可以被用于大对象的创建。第三中方法是将堆空间预先分为两部分,只在其中一部分新建对象,当这部分空间用完时,将其中的存活对象拷贝到另一部分,然后清空这部分的空间即可。


分代回收

JVM中绝大多数新建对象的生命周期都很短,可能创建出来执行相应操作后马上就没用了,因此绝大部分是可以回收的,只有少数对象会被持续使用。因此JVM将对象分为新生代对象和老年代对象。所有新创建的对象都被放置在新生代内存区,新生代还分为了Eden、From、To三个区,在垃圾回收过程中按顺序逐级将存活对象移到下一级,直到进入老年代内存区。

垃圾回收器

早期单核CPU时代,JVM在进行垃圾回收的时候需要暂停住所有正在运行的工作线程,这一步被称为stop-the-world,然后启动一个垃圾回收线程进行垃圾回收,回收完之后继续运行各个工作线程。后来有了多核CPU,支持多线程并行运行,于是stop-the-world之后的垃圾回收线程从一个扩展到多个,以并行的方式进行垃圾回收,从而极大缩短了工作线程暂停的时间。为了进一步减少工作线程被暂停的情况,又出现了并发回收机制,即将垃圾回收分为多个阶段,在第一轮标记的时候,垃圾回收线程与工作线程并发运行,然后进入stop-the-world,对标记进行检查更新,再恢复工作线程,让垃圾回收线程以并发的方式进行清理。

最新的G1垃圾回收器仍然将内存分为年轻代和老年代,年轻代又分为Eden和Survivor两类,老年代分为Old和Humongous两类,但是两代的内存空间不再是连续存储,而是四种类型的内存段混合存储。G1垃圾回收器将内存分为2048左右个段,每个段有唯一的类型。在执行垃圾回收时,先并发地进行标记,然后将Eden中的存活对象复制到Survivor,而老年代的两种类型的对象都会被回收。

设计一个秒杀系统,主要的挑战和问题有哪些?核心的架构方案或者思路有哪些?

相关文章

网友评论

      本文标题:架构师训练营第9周作业 JVM垃圾回收 秒杀架构

      本文链接:https://www.haomeiwen.com/subject/rosgrktx.html