今天去看牙医,他问我年级轻轻牙齿怎么磨损这么严重?我说,没有人点赞的这些年,我都是咬着牙过来的。

Java中的垃圾回收器几乎是面试中的必考点,无论是面试初级,中级还是高级,总免不了要问一问垃圾回收器的一些知识点。不管在实际开发中你使用程度怎么样,为了面试不被压价,还是非常有必要对它做一个较深入的理解。

本篇对JVM中常用的几种垃圾回收器的主要特点,使用场景及优化建议做一个简单介绍,希望起到抛砖引玉的效果,对你入门有所帮助。

新生代回收器

  • Serial
  • ParNew
  • parallel

老年代回收器

  • Serial Old
  • CMS
  • Parallel Old

新生代和老年代回收器

  • G1

Serial

特点

Serial收集器是最基本、发展历史最悠久的收集器。JDK1.3.1前是HotSpot新生代收集的唯一选择。

运行示意图

有如下特点:

  • 针对新生代;
  • 采用复制算法;
  • 单线程收集;
  • 进行垃圾收集时,必须暂停所有工作线程,直到完成;
优势:

简单高效,由于采用的是单线程的方法,因此与其他类型的收集器相比,对单个cpu来说没有了上下文之间的的切换,效率比较高。

劣势:

会在用户不知道的情况下停止所有工作线程。

使用场景

  • Client 模式(桌面应用)

在用户的桌面应用场景中,可用内存一般不大,可以在较短时间内完成垃圾收集,只要不频繁发生,这是可以接受的

  • 单核服务器

对于限定单个CPU的环境来说,Serial收集器没有线程切换开销,可以获得最高的单线程收集效率

参数设置

  • -XX:+UseSerialGC:添加该参数来显式的使用串行垃圾收集器

ParNew

特点

ParNew收集器其实就是Serial收集器的多线程版本,除了使用多线程进行垃圾收集之外,其余均和Serial 收集器一致。

运行示意图

优势:

多线程版本的Serial,可以更加有效的利用系统资源

劣势:

同Serial,会在用户不知道的情况下停止所有工作线程

使用场景

Server模式下使用,亮点是除Serial外,目前只有它能与CMS收集器配合工作,是一个非常重要的垃圾回收器。

参数设置

  • -XX:+UseConcMarkSweepGC:指定使用CMS后,会默认使用ParNew作为新生代收集器;
  • -XX:+UseParNewGC:强制指定使用ParNew;
  • -XX:ParallelGCThreads:指定垃圾收集的线程数量,ParNew默认开启的收集线程与CPU的数量相同;

parallel

特点

Parallel Scavenge也是一款用于新生代的多线程收集器,也是采用复制算法。与ParNew的不同之处在于Parallel Scavenge收集器的目的是达到一个可控制的吞吐量,而ParNew收集器关注点在于尽可能的缩短垃圾收集时用户线程的停顿时间。

运行示意图

有如下特点:

  • 新生代收集器;
  • 采用复制算法;
  • 多线程收集;
  • 关注点与其他收集器不同:
    • CMS等收集器的关注点是尽可能地缩短垃圾收集时用户线程的停顿时间;
    • 而Parallel Scavenge收集器的目标则是达一个可控制的吞吐量;
优势:

追求高吞吐量,高效利用CPU,是吞吐量优先,且能进行精确控制。

劣势:

应该说是特点,追求高吞吐量必然要牺牲一些其他方面的优势,不能做到既,又。ParNew收集器关注点在于尽可能的缩短垃圾收集时用户线程的停顿时间,原本10s收集一次, 每次停顿100ms, 设置完参数之后可能变成5s收集一次, 每次停顿70ms. 停顿时间变短, 但收集次数变多。

使用场景

根据相关特性,我们很容易想到它的使用场景,即:当应用程序运行在具有多个CPU上,对暂停时间没有特别高的要求时,程序主要在后台进行计算,而不需要与用户进行太多交互等就特别适合ParNew收集器。

  • 例如,那些执行批量处理、订单处理、工资支付、科学计算的应用程序等

参数设置

  • -XX:MaxGCPauseMillis:控制最大垃圾收集停顿时间,大于0的毫秒数;
  • -XX:GCTimeRatio:设置垃圾收集时间占总时间的比率,0<n<100的整数;

Serial Old

特点

Serial Old是Serial收集器的老年代版本,同样是一个单线程收集器,使用标记-整理算法。

有如下特点:

  • 针对老年代;
  • 采用"标记-整理"算法(还有压缩,Mark-Sweep-Compact);
  • 单线程收集;

优劣势基本和Serial无异,它是和Serial收集器配合使用的老年代收集器。

使用场景

  • Client模式;
  • 单核服务器;
  • 与Parallel Scavenge收集器搭配;
  • 作为CMS收集器的后备方案,在并发收集发生Concurrent Mode Failure时使用

CMS

特点

CMS(Concurrent Mark Sweep)收集器是一种以获取最短回收停顿时间为目标的收集器。采用的算法是“标记-清除”,运作过程分为四个步骤:

  • 初始标记,标记GC Roots 能够直接关联到达对象
  • 并发标记,进行GC Roots Tracing 的过程
  • 重新标记,修正并发标记期间因用户程序继续运作而导致标记产生变动的那一部分标记记录
  • 并发清除,用标记清除算法清除对象。

运行示意图

有如下特点:

  • 针对老年代;
  • 基于"标记-清除"算法(不进行压缩操作,产生内存碎片);
  • 以获取最短回收停顿时间为目标;
  • 并发收集、低停顿;
  • 需要更多的内存(看后面的缺点);
优势:
  • 停顿时间短;
  • 吞吐量大;
  • 并发收集
劣势:
  • 对CPU资源非常敏感
  • 无法收集浮动垃圾
  • 容易产生大量内存碎片

使用场景

  • 与用户交互较多的场景;
  • 希望系统停顿时间最短,注重服务的响应速度;
  • 以给用户带来较好的体验;

如常见WEB、B/S系统的服务器上的应用。

参数设置

  • -XX:+UseConcMarkSweepGC:指定使用CMS收集器

Parallel Old

特点

Parallel Old是Parallel Scavenge收集器的老年代版本,使用多线程和“标记-整理”算法,可以充分利用多核CPU的计算能力。

有如下特点:

  • 针对老年代;
  • 采用"标记-整理"算法;
  • 多线程收集;

优劣势参考Parallel Scavenge收集器。

使用场景

  • JDK1.6及之后用来代替老年代的Serial Old收集器;
  • 特别是在Server模式,多CPU的情况下;

这样在注重吞吐量以及CPU资源敏感的场景,就有了Parallel Scavenge(新生代)加Parallel Old(老年代)收集器的"给力"应用组合;

参数设置

  • -XX:+UseParallelOldGC:指定使用Parallel Old收集器

G1

特点

G1(Garbage-First)是JDK7-u4才推出商用的收集器

  • 并行与并发:G1能充分利用多CPU,多核环境下的硬件优势。
  • 分代收集:能够采用不同的方式去处理新创建的对象和已经存活了一段时间的对象,不需要与其他收集器进行合作。
  • 空间整合:G1从整体上来看基于“标记-整理”算法实现的收集器,从局部上看是基于复制算法实现的,因此G1运行期间不会产生空间碎片。
  • 可预测的停顿:G1能建立可预测的时间停顿模型,能让使用者明确指定一个长度为M毫秒的时间片段内,消耗在垃圾收集上的时间不得超过N毫秒。

运行示意图

有如下特点:

  • 并行与并发
  • 分代收集,收集范围包括新生代和老年代
  • 结合多种垃圾收集算法,空间整合,不产生碎片
  • 可预测的停顿:低停顿的同时实现高吞吐量
  • 面向服务端应用,将来替换CMS
优势:
  • 能充分利用多CPU、多核环境下的硬件优势;
  • 能独立管理整个GC堆(新生代和老年代),而不需要与其他收集器搭配;
  • 不会产生内存碎片,有利于长时间运行;
  • 除了追求低停顿处,还能建立可预测的停顿时间模型;

G1收集器是当今收集器技术发展的最前沿成果。

劣势:

G1 需要记忆集 (具体来说是卡表)来记录新生代和老年代之间的引用关系,这种数据结构在 G1 中需要占用大量的内存,可能达到整个堆内存容量的 20% 甚至更多。而且 G1 中维护记忆集的成本较高,带来了更高的执行负载,影响效率。

按照《深入理解Java虚拟机》作者的说法,CMS 在小内存应用上的表现要优于 G1,而大内存应用上 G1 更有优势,大小内存的界限是6GB到8GB。

所以,尽管是最前沿的成果,也不是完美无缺的。

使用场景

个人以为G1已经基本全面压制cms、parallel等回收器,缺点见上面的劣势。但如果不是追求极致的性能,基本可以无脑G1

参数设置

  • -XX:+UseG1GC:指定使用G1收集器;
  • -XX:InitiatingHeapOccupancyPercent:当整个Java堆的占用率达到参数值时,开始并发标记阶段;默认为45;
  • -XX:MaxGCPauseMillis:为G1设置暂停时间目标,默认值为200毫秒;
  • -XX:G1HeapRegionSize:设置每个Region大小,范围1MB到32MB;目标是在最小Java堆时可以拥有约2048个Region;

基本就介绍这些了,垃圾回收器基本不变的知识点多,学会(理解)可以应付N年的相关知识的面试,又是高频面试考点,各位同学还是值得在这块下点功夫的。文中有任何不足,错误欢迎指出,共同进步!

面试官:说一下JVM常用垃圾回收器的特点、优劣势、使用场景和参数设置的更多相关文章

  1. 面试官,Java8 JVM内存结构变了,永久代到元空间

    在文章<JVM之内存结构详解>中我们描述了Java7以前的JVM内存结构,但在Java8和以后版本中JVM的内存结构慢慢发生了变化.作为面试官如果你还不知道,那么面试过程中是不是有些露怯? ...

  2. 【JVM】垃圾回收器总结(2)——七种垃圾回收器类型

    七种垃圾回收器类型 GC的约定参数 DefNew——Default New Generation Tenured——Serial Old ParNew——Parallel New Generation ...

  3. 面试官:ElasticSearch是什么,它有什么特性与使用场景?

    哈喽!大家好,我是小奇,一位热爱分享的程序员 小奇打算以轻松幽默的对话方式来分享一些技术,如果你觉得通过小奇的文章学到了东西,那就给小奇一个赞吧 文章持续更新 一.前言 书接上回,我本以为我跟面试我的 ...

  4. 面试官问我JVM调优,我忍不住了!

    面试官:今天要不来聊聊JVM调优相关的吧? 面试官:你曾经在生产环境下有过调优JVM的经历吗? 候选者:没有 面试官:... 候选者:嗯...是这样的,我们一般优化系统的思路是这样的 候选者:1. 一 ...

  5. 深入探究JVM之垃圾回收器

    @ 目录 前言 正文 一.垃圾收集算法 标记-复制 标记-清除 标记-整理 分代回收 二.常用的垃圾回收器 Serial/SerialOld ParNew Parallel Scavenge/Para ...

  6. 面试官问我JVM内存结构,我真的是

    面试官:今天来聊聊JVM的内存结构吧? 候选者:嗯,好的 候选者:前几次面试的时候也提到了:class文件会被类加载器装载至JVM中,并且JVM会负责程序「运行时」的「内存管理」 候选者:而JVM的内 ...

  7. 深入理解JVM一垃圾回收器

    上一篇我们介绍了常见的垃圾回收算法,不同的算法各有各的优缺点,在JVM中并不是单纯的使用某一种算法进行垃圾回收,而是将不同的垃圾回收算法包装在不同的垃圾回收器当中,用户可以根据自身的需求,使用不同的垃 ...

  8. 一文了解JVM全部垃圾回收器,从Serial到ZGC

    <对象搜索算法与回收算法>介绍了垃圾回收的基础算法,相当于垃圾回收的方法论.接下来就详细看看垃圾回收的具体实现. 上文提到过现代的商用虚拟机的都是采用分代收集的,不同的区域用不同的收集器. ...

  9. jvm学习-垃圾回收器(四)

    说明 各种垃圾回收算法都有各自的优缺点.jvm也并没有只采用一种垃圾算法.并提供几种组合供我根据场景进行选择. jvm内存结构 Person p=new Person(); 1.程序里面创建一个对象会 ...

随机推荐

  1. 【aws-系统】简单的SNS到电报通知机器人

    动机 我已经使用此设置几个月了,这是我的用例: 预定的提醒.我有一些安排好的CloudWatch Events,以提醒我有关各种日常活动以及我从文章和书籍中保存的想法数据库中的随机推销的信息. 应用程 ...

  2. Social engineering tookit 钓鱼网站

    目录 Set 钓鱼攻击 网站克隆 Set Set(Social engineering tookit)是一款社会工程学工具,该工具用的最多的就是用来制作钓鱼网站. Kali中自带了该工具. 钓鱼攻击 ...

  3. 使用BurpSuite抓取HTTPS网站的数据包

    昨天面试,技术官问到了我如何使用BurpSuite抓取https网站的数据包,一时间没能回答上来(尴尬!).因为以前https网站的数据包我都是用Fiddler抓取的,Fiddlert自动帮我们配置好 ...

  4. 怎样用jquery添加HTML代码

    方法一: $(".demo").html("<span></span>") 方法二: var $span=$("<spa ...

  5. Vip视频解析端口

    ------------恢复内容开始------------ 本教程仅供学习交流使用,请不要用于商业用途,支持正版,人人有责 我们怎么免费看VIP视频呢?一个简单的方法,就是通过解析接口 VIP视频解 ...

  6. 【Redis】redis异步消息队列+Spring自定义注解+AOP方式实现系统日志持久化

    说明: SSM项目中的每一个请求都需要进行日志记录操作.一般操作做的思路是:使用springAOP思想,对指定的方法进行拦截.拼装日志信息实体,然后持久化到数据库中.可是仔细想一下会发现:每次的客户端 ...

  7. Spring MVC工作原理及源码解析(四) ViewResolver实现原理及源码解析

    0.ViewResolver原理介绍 根据视图的名称将其解析为 View 类型的视图,如通过 ModelAndView 中的视图名称将其解析成 View,View 是用来渲染页面的,也就是将 Mode ...

  8. MFC的六大机制

    MFC的六大机制 程序的初始化过程 运行时类型识别 动态创建 永久保存 消息映射 命令传递 运行时类型识别 MFC的运行时类型识别就是在程序运行过程中判断某个对象是否属于某个类,MFC通过为需要进行运 ...

  9. 面试遇到的坑JS深拷贝和浅拷贝

    首先要搞明白深拷贝和钱拷贝的区别要先搞明白 栈和堆的区别 一.栈 栈存储基础数据类型,如: String.Number.Boolean.Null.Underined,这些简单的基础数据类型能够直接存储 ...

  10. 『动善时』JMeter基础 — 19、JMeter配置元件【随机变量】

    目录 1.随机变量介绍 2.随机变量界面详解 3.随机变量的使用 (1)测试计划内包含的元件 (2)线程组界面内容 (3)随机变量界面内容 (4)HTTP请求界面内容 (5)查看结果 1.随机变量介绍 ...