Serial 收集器:
简介:
串行收集器。JVM运行在Client模式下,默认的新生代收集器,采用复制回收算法。
Serial 串行(单线程)收集器它的“单线程”的意义不仅仅说明它只会采用一个Cup或者一条收集线程来进行垃圾收集工作,更重要的是它在进行垃圾收集工作时,会进行Stop The Word(停止其他所有的工作线程,直到垃圾收集结束),不仅仅是Serial收集器其他收集器也都会进行STW,只是停顿时间长短。
优点:
简单高效(与其他收集器的单线程相比),对于限定单个CUP的环境来说,Serial收集器由于没有线程交互的开销,专心做垃圾收集自然可以获取最高的单线程收集效率。适用于用户桌面应用场景中。
ParNew收集器:
ParNew收集器其实是Serial收集器的多线程版本。JVM运行在Server模式下首选新生代收集器。
除了多线程收集以外其他与Serial收集器相比没有太多的创新之处,但是除了Serial之外,目前只有他能够与CMS收集器配合工作。
在单CPU环境中ParNew绝对不会有比Serial更好的效果。甚至由于存在线程交互开销,该收集器在通过超线程实现的两个CPU环境中都不能保证会百分百超越Serial收集器。当然,随着可以使用的CUP数量增加,它对于GC时系统资源的有效利用还是很有好处的。
它默认开启的收集线程数与CUP数量相同,在CPU数量非常多的情况下,可以使用 -XX:ParallelGCThreads参数来控制收集线程数量。
Parallel【并行】 Scavenge收集器:
并行收集器。Parallel Scavenge收集器同样也是一个新生代收集器,采用复制回收算法,又是并行的多线程收集器…
看上去似乎和ParNew没有任何区别。但是实际上它的关注点和其他收集器不同。其他收集器的关注点是尽可能的缩短垃圾收集时用户线程停顿时间,而Parallel Scavenge收集器的目标则是达到一个可控制的吞吐量(Throughput)。
支持自适应调节策略。-XX:UseAdaptiveSizePolicy。设置此参数后会由虚拟机动态调节Eden、Survivor区的比例以及晋级老年代对象年龄等细节参数以提供最合适的停顿时间或者最大的吞吐量。需要设置优化目标。XX:MaxGCPauseMillis/XX:GCTimeRatio。
Serial Old收集器
串行收集器,采用标记整理算法,是Serial老年代收集器。
目前主要作为CMS收集器后备预案,并在收集器发生 Concurrent Mode Failure 时使用。(在jdk1.5之前由于没有Parallel Old收集器,可与Parallel Scavenge 收集器搭配使用,但效率低下)
Parallel Old 收集器
并行收集器,采用标记整理算法,Parallel Scavenge 收集器的老年代版本。
jdk1.6开始提供,出现之后“吞吐量优先级”收集器才有了名副其实的应用组合。
CMS(Concurrent【并发】 Mark Sweep 并发标记清除):
采用标记清除算法,老年代的回收器。以获取最短停顿时间为目标。(在重视服务器响应速度,为用户带来更好的体验场景中使用)。
运作过程:
- 初始标记:初始标记只是标记一下GC Root能直接关联到的对象,速度很快。
- 并发标记:进行GC Root Tracing。
- 重新标记:修正并发标记期间因用户线程继续运作产生的相对于初始标记变动的部分。比初始标记时间长,低于并发标记。
- 标记清除
初始标记、重新标记仍然需要STW(Stop The Word)。
缺点:
- 对CPU资源非常敏感。
其实,面向并发设计的程序对CPU资源都比较敏感。在并发阶段,它虽然不会导致用户线程停顿,但是会因为占用了一部分CPU资源(线程)而导致应用程序变慢,总吞吐量降低。CMS默认启动回收线程数是(CPU数量+3)/4,也就是说当CPU在4个以上时,并发回收垃圾收集线程不低于25%的CPU资源,并随着CPU数量增多而下降。不足4个时,对应用程序影响很大。 - 无法处理浮动垃圾,可能出现 “Concurrent Mode Failure”失败而导致另一次Full GC的产生。
备注
并行(Parallel)与并发(Concurrent):
并行是指多条垃圾收集线程并行工作,但是此时用户线程仍然处于等待状态。
并发是指垃圾收集线程与用户线程同时执行,用户线程扔在继续工作,而垃圾收集线程运行在另一个CUP上(但不一定是并行的,可能会交替执行)。
参数 | 描述 |
---|---|
-XX:+UseSerialGC | Jvm运行在Client模式下的默认值,打开此开关后,使用Serial + Serial Old的收集器组合进行内存回收 |
-XX:+UseParNewGC | 打开此开关后,使用ParNew + Serial Old的收集器进行垃圾回收 |
-XX:+UseConcMarkSweepGC | 使用ParNew + CMS + Serial Old的收集器组合进行内存回收,Serial Old作为CMS出现“Concurrent Mode Failure”失败后的后备收集器使用。 |
-XX:+UseParallelGC | Jvm运行在Server模式下的默认值,打开此开关后,使用Parallel Scavenge + Serial Old的收集器组合进行回收 |
-XX:+UseParallelOldGC | 使用Parallel Scavenge + Parallel Old的收集器组合进行回收 |
-XX:SurvivorRatio | 新生代中Eden区域与Survivor区域的容量比值,默认为8,代表Eden:Subrvivor = 8:1 |
-XX:PretenureSizeThreshold | 直接晋升到老年代对象的大小,设置这个参数后,大于这个参数的对象将直接在老年代分配 |
-XX:MaxTenuringThreshold | 晋升到老年代的对象年龄,每次Minor GC之后,年龄就加1,当超过这个参数的值时进入老年代 |
-XX:+HandlePromotionFailure | 是否允许新生代收集担保,进行一次minor gc后, 另一块Survivor空间不足时,将直接会在老年代中保留 |
-XX:ParallelGCThreads | 设置并行GC进行内存回收的线程数 |
-XX:GCTimeRatio | GC时间占总时间的比列,默认值为99,即允许1%的GC时间,仅在使用Parallel Scavenge 收集器时有效 |
-XX:MaxGCPauseMillis | 设置GC的最大停顿时间,在Parallel Scavenge 收集器下有效 |
-XX:UseAdaptiveSizePolicy | 设置此参数后会由虚拟机动态调节Eden、Survivor区的比例以及晋级老年代对象年龄等细节参数以提供最合适的停顿时间或者最大的吞吐量,在Parallel Scavenge 收集器下有效 |
-XX:CMSInitiatingOccupancyFraction | 设置CMS收集器在老年代空间被使用多少后出发垃圾收集,默认值为68%,仅在CMS收集器时有效,-XX:CMSInitiatingOccupancyFraction=70 |
-XX:UseCMSCompactAtFullCollection | 由于CMS收集器会产生碎片,此参数设置在垃圾收集器后是否需要一次内存碎片整理过程,仅在CMS收集器时有效 |
-XX:+CMSFullGCBeforeCompaction | 设置CMS收集器在进行若干次垃圾收集后再进行内存碎片整理过程,通常与UseCMSCompactAtFullCollection参数一起使用 |
-XX:+UseFastAccessorMethods | 原始类型优化 |
-XX:+DisableExplicitGC | 是否关闭手动System.gc |
-XX:+CMSParallelRemarkEnabled | 降低标记停顿 |
-XX:LargePageSizeInBytes | 内存页的大小不可设置过大,会影响Perm的大小,-XX:LargePageSizeInBytes=128m |
Client、Server模式默认GC
新生代GC方式 | 老年代和持久代GC方式 | |
---|---|---|
Client | Serial 串行GC | Serial Old 串行GC |
Server | Parallel Scavenge 并行回收GC | Parallel Old 并行GC |