【第二章:Java核心技术解析】第12节:Java进阶 - JVM内存机制(中)


大家好,上一小节中我们主要介绍了JVM内存机制的基础知识点,包括内存的分配以及回收策略等。本小节我们主要介绍垃圾回收算法以及垃圾收集器,并且对当前使用较广的CMS垃圾收集器做了较为详细的阐述。垃圾回收算法是JVM相关技术考察中的高频考点,希望大家可以有效理解与掌握,在面试中清晰阐述。

有效掌握JVM内存相关技术原理对于我们的日常开发工作也有很大的帮助。好了,让我们一起来学习吧~

(1)JVM垃圾回收算法有哪些?(重点掌握)

答:HotSpot 虚拟机采用了root根搜索方法来进行内存回收,常见的回收算法有标记-清除算法,复制算法和标记整理算法。

标记-清除算法(Mark-Sweep):

标记-清除算法执行分两阶段。第一阶段从引用根节点开始标记所有被引用的对象,第二阶段遍历整个堆,把未标记的对象清除。此算法需要暂停整个应用,并且会产生内存碎片。

图片说明


复制算法:

复制算法把内存空间划为两个相等的区域,每次只使用其中一个区域。垃圾回收时,遍历当前使用区域,把正在使用中的对象复制到另外一个区域中。复制算法每次只处理正在使用中的对象,因此复制成本比较小,同时复制过去以后还能进行相应的内存整理,不会出现“碎片”问题。当然,此算法的缺点也是很明显的,就是需要两倍内存空间。

图片说明


标记-整理算法:

标记-整理算法结合了“标记-清除”和“复制”两个算法的优点。也是分两阶段,第一阶段从根节点开始标记所有被引用对象,第二阶段遍历整个堆,清除未标记对象并且把存活对象“压缩”到堆的其中一块,按顺序排放。此算法避免了“标记-清除”的碎片问题,同时也避免了“复制”算法的空间问题。

图片说明


解析:

垃圾回收算法是垃圾收集器的算法实现基础,年轻代垃圾回收一般采用复制算法,老年代垃圾回收一般采用标记-清除和标记-整理算法。希望大家对照着算法示意图,对算法的原理与过程加以理解与掌握。接下来,我们一起来看垃圾回收算法的具体实现,那就是垃圾收集器吧。


(2)JVM中的垃圾收集器有了解吗?(重点掌握CMS收集器)

答: JVM中的垃圾收集器主要包括7种,即Serial,Serial Old,ParNew,Parallel Scavenge,Parallel Old以及CMS,G1收集器。如下图所示:

图片说明

Serial收集器:

Serial收集器是一个单线程的垃圾收集器,并且在执行垃圾回收的时候需要 Stop The World。虚拟机运行在Client模式下的默认新生代收集器。Serial收集器的优点是简单高效,对于限定在单个CPU环境来说,Serial收集器没有多线程交互的开销。

Serial Old收集器:

Serial Old是Serial收集器的老年代版本,也是一个单线程收集器。主要也是给在Client模式下的虚拟机使用。在Server模式下存在主要是做为CMS垃圾收集器的后备预案,当CMS并发收集发生Concurrent Mode Failure时使用。

ParNew收集器:

ParNew是Serial收集器的多线程版本,新生代是并行的(多线程的),老年代是串行的(单线程的),新生代采用复制算法,老年代采用标记整理算法。可以使用参数:-XX:UseParNewGC使用该收集器,使用 -XX:ParallelGCThreads可以限制线程数量。

Parallel Scavenge垃圾收集器:

Parallel Scavenge是一种新生代收集器,使用复制算法的收集器,而且是并行的多线程收集器。Paralle收集器特点是更加关注吞吐量(吞吐量就是cpu用于运行用户代码的时间与cpu总消耗时间的比值)。可以通过-XX:MaxGCPauseMillis参数控制最大垃圾收集停顿时间;通过-XX:GCTimeRatio参数直接设置吞吐量大小;通过-XX:+UseAdaptiveSizePolicy参数可以打开GC自适应调节策略,该参数打开之后虚拟机会根据系统的运行情况收集性能监控信息,动态调整虚拟机参数以提供最合适的停顿时间或者最大的吞吐量。自适应调节策略是Parallel Scavenge收集器和ParNew的主要区别之一。

Parallel

剩余60%内容,订阅专栏后可继续查看/也可单篇购买

Java开发岗高频面试题全解析 文章被收录于专栏

<p> Java开发岗高频面试题全解析,专刊正文共计31节,已经全部更新完毕。专刊分9个模块来对Java岗位面试中的知识点进行解析,包括通用面试技能,Java基础,Java进阶,网络协议,常见框架以及算法,设计模式等。专刊串点成面的解析每个面试题背后的技术原理,由浅入深,循序渐进,力争让大家掌握面试题目的背后的技术原理,摒弃背题模式的陋习。 专刊详细信息,请查阅专刊大纲和开篇词的介绍。 本专刊购买后即可解锁所有章节,故不可以退换哦~ </p> <p> <br /> </p>

全部评论
垃圾收集器总结: 最初使用Serial+Serial Old收集垃圾,最简单,两者都是单线程的,所以只适合少内存使用。 随着内存增大,开始使用Parallel Scavenge +Parallel Old , 这两个其实就是前面两个Serial的多线程版本,性能更好一点,在JDK1.6-1.8中作为默认垃圾回收器。 随着内存进一步增大,出现了ParNew+CMS的组合,其中ParNew是Parallel Scavenge为了配合CMS出现的改进版本,CMS是并发标记清除。看似性能更好,实则存在巨大的缺陷:CMS会导致大量的内存碎片, 而内存碎片太多的时候,会使用Serial Old这个单线程的收集器进行垃圾收集(雾).... 从JDK1.7之后出现了G1垃圾收集器,在JDK1.8之后开始完善,它支持更大的内存(大概几百G),特点是逻辑分代,物理不分代,它的stop-the-world时间可以小于200ms。还有一个在JDK11中推出的垃圾回收器ZGC,还正在开发,它的逻辑、物理都不分代,而且能支持16T的内存,传说停顿时间只有1ms(***C++!)
8 回复 分享
发布于 2020-02-29 10:39
最重点的是。。说这几种算法都没用,面试官问你JVM的垃圾回收算法是什么,标准答案应该是:JVM这三种都不用,用的是分代回收算法。然后再详细阐述年轻代有哪种算法,老年代有哪种算法,这样回答才是满分。
4 回复 分享
发布于 2020-03-11 09:56
这篇没懂
1 回复 分享
发布于 2020-01-01 16:17
打卡
点赞 回复 分享
发布于 2023-09-08 18:39 河南
请问复制算法需要暂停整个应用吗
点赞 回复 分享
发布于 2020-09-15 13:51
二刷打卡
点赞 回复 分享
发布于 2020-08-20 14:17
Jul 18打卡
点赞 回复 分享
发布于 2020-07-19 11:08
打卡
点赞 回复 分享
发布于 2020-02-24 21:52
打卡
点赞 回复 分享
发布于 2020-01-18 20:45
打卡,这块我还要好好练一练
点赞 回复 分享
发布于 2020-01-03 19:39

相关推荐

06-11 17:39
门头沟学院 Java
小呆呆的大鼻涕:卧槽,用户彻底怒了
点赞 评论 收藏
分享
Twilight_m...:经典我朋友XXXX起手,这是那种经典的不知道目前行情搁那儿胡编乱造瞎指导的中年人,不用理这种**
点赞 评论 收藏
分享
评论
4
收藏
分享

创作者周榜

更多
牛客网
牛客网在线编程
牛客网题解
牛客企业服务