JVM常用调优方法

一、常用调优方法

1、将新对象预留在新生代

由于 Full GC 的成本要远远高于 Minor GC ,因此尽可能将对象分配在新生代,在JVM 调优中,可以为应用程序分配一个合理的新生代空间,以最大限度避免新对象直接进去老年代。

注意:由于新生代垃圾回收的速度高于老年代回收,因此,将年轻对象预留在新生代有利于提高整体的 GC 效率

2、大对象进入老年代

大对象占用空间多,直接放入新生代中会扰乱新生代GC,新生代空间不足将会把大量的较小的年轻代对象移入到老年代中,这对GC来说是相当不利的。如果有短命大对象,对GC来说将会是一场灾难,原本存放于老年代的永久对象,被短命大对象塞满,扰乱了分代内存回收的基本思路,因此,在开发过程中,尽可能避免使用短命的大对象。使用参数 -XX:PretenureSizeThreshold 设置大对象直接进入老年代的阀值,当对象超过这个阀值时,将直接在老年代中分配。其中, -XX:PretenureSizeThreshold 只对串行收集器和新生代并行收集器有效,并行回收收集器不识别这个参数。

注意:短命的大对象对垃圾回收是一场灾难,目前木有一种特别好的回收方法处理这个问题,因此尽可能避免使用短命的大对象。

3、设置对象进入老年代的年龄

在堆中每个对象都有自己的年龄,如果对象在 eden 区,经过一次 GC 后还存活,则被移动到 survivor 区中,对象年龄加 1,以后每经过一次 GC 依然存活的,对象年龄就加 1。当对象年龄达到阀值时,就移动到老年代,这个阀值用以下参数设置:

-XX:MaxTenuringThreshold:默认值是15,这个参数是指定进入老年代的最大年龄值,对象实际进入老年代的年龄是 JVM 在运行时根据内存使用情况动态计算的。

如果希望对象尽可能长地留在新生代中,可以设置一个较大的阀值。

4、稳定与震荡的堆大小

稳定的堆大小对垃圾回收是有利的,获得一个稳定堆大小的方法就是设置 -Xmx 和 -Xms 一样的值。不稳定的堆也不是木有用处,让堆大小在一个区间内震荡,在系统不需要使用大内存时压缩堆空间,使 GC 应对一个较小的堆,可以加快单次 GC 的速度。基于这种思想,JVM 提供了两个参数用于压缩和扩展堆空间,参数如下:

-XX:MinHeapFreeRatio:设置堆空间最小空闲比例,默认是 40 ,当堆空间的空闲比例小于这个值时,JVM 便会扩展堆空间

-XX:MaxHeapFreeRatio:设置堆空间的最大空闲比例,默认是 70,当堆空间的空闲比例大于这个值时,JVM 便会压缩堆空间,得到一个较小的堆

注意:当 -Xms 和 -Xmx 相等时,-XX:MinHeapFreeRatio 和 -XX:MaxHeapFreeRatio 这两个参数无效

5、吞吐量优先设置

机器配置是 4G 内存 和 32 核 CPU,配置参数如下:

-Xms3800m -Xmx3800m(堆的初始值和最大值一样)

-Xmn2g(新生代大小)

-Xss128k(线程栈大小,减少它使剩余的系统内存支持更多的线程)

-XX:+UseParallelGC(新生代使用并行回收收集器)

-XX:ParallelGCThreads=20(垃圾回收的线程数)

-XX:+UseParallelOldGC (老年代使用并行回收收集器)

6、使用大页案例

使用大的内存分页可以增强 CPU 的内存寻址能力,从而提高系统的性能,参数设置如下:

-XX:LargePageSizeInBytes:设置大页的大小

7、降低停顿案例

为了降低应用软件在垃圾回收时的停顿,首先考虑的使用关注系统停顿的 CMS 回收器,为了减少 Full GC 的次数,应尽可能将对象预留在新生代,新生代 Minor GC 的成本远远小于老年代的 Full GC

-Xms3800m -Xmx3800m(堆的初始值和最大值一样)

-Xmn2g(新生代大小)

-Xss128k(线程栈大小,减少它使剩余的系统内存支持更多的线程)

-XX:ParallelGCThreads=20(垃圾回收的线程数)

-XX:+UseConcMarkSweepGC(老年代使用 CMS 收集器)

-XX:+UseParNewGC(新生代使用并行收集器)

-XX:SurvivorRatio=8(设置 eden : survivor = 8 : 1)

-XX:TargetSurvivorRatio(设置 survivor 的使用率为 90%,默认是50%,提高了survivor 区的使用率,当存放的对象超过这个数值,则对象会向老年代压缩)

-XX:MaxTenuringThreshold=31(设置年轻对象晋升到老年代的最大年龄是31,默认是15,设为31是尽可能地将对象留在新生代)

二、常用JVM参数

1、JIT编译参数

JVM 的 JIT(Just-In-Time)编译器,可以在运行时将字节码编译成本地代码,从而提高函数的执行效率。参数设置如下

-XX:CompileThreshold:JIT 编译的阀值,当函数的调用超过这个值时,JIT 就将字节码编译成本地机器码。在 client 模式下,取值是 1500,在 server 模式下,取值是 10000

2、堆快照(堆 Dump)

在性能问题排查中,分析堆快照(Dump)是必不可少的一环。获取程序的堆快照文件有多种方法,下面介绍一种常用的方法,即使用 -XX:+HeapDumpOnOutOfMemoryError 参数在程序发生 OOM 时,导出应用程序的当前堆快照。这是一种非常有效的方法,因为当程序发生 OOM 退出系统时,一些瞬时信息都随着程序的终止而消失,而重现 OOM 问题往往比较困难或者耗时,因此当发生 OOM 时,将堆信息保存到文件中是至关重要的,通过下面的参数设置:

-XX:+HeapDumpOnOutOfMemoryError(开启堆快照)

-XX:HeapDumpPath=C:/m.hprof(保存文件到哪个目录)

导出的 Dump 文件可以通过 Visual VM 等多种工具查看分析,进而定位问题,如下图所示:

3、错误处理

系统发生 OOM 错误时,JVM 在错误发生时运行一段第三方脚本,重置系统,设置参数如下:

-XX:OnOutOfMemoryError=C:\reset.bat

4、获取 GC 信息

获取 GC 信息是 java 应用程序调优最重要的一环,下面介绍一些常用的设置参数:

-XX:+PrintGC(-verbose:gc):输出打印简要的 GC 信息,包括 GC 前的堆栈情况和 GC 后的堆栈大小和堆栈的总大小

-XX:+PrintGCDetails:输出打印详细的 GC 信息,不仅包括基本信息,还给出了新生代、老年代和永久区各自的 GC 信息

-XX:+PrintGCTimeStamps:额外输出 GC 发生的时间,可以推断出 GC 的频率和间隔

-XX:+PrintTenuringDistribution -XX:MaxTenuringThreshold=18:查看新生代晋升老年代的实际阀值(-XX:+PrintTenuringDistribution),设置的最大年龄为18( -XX:MaxTenuringThreshold=18)

-XX:+PrintHeapAtGC:每次 GC 时都会打印堆的详细使用情况,输出量很巨大。它分为两个部分:GC 前的堆信息和 GC 后的堆信息,这里包含了新生代、老年代和永久区的使用大小和使用率,还包括了新生代中 eden 区和 survivor 区的使用情况

-XX:+PrintGCApplicationStoppedTime:应用程序在 GC 发生时的停顿时间

-XX:+PrintGCApplicationConcurrentTime:应用程序在 GC 停顿期间的执行时间

-Xloggc:C:/gc.log:将 GC 日志信息输出到具体位置的文件中,便于日后日志分析

注意:详细的 GC 信息是进行 JVM 调优的重要参考信息,可以根据 GC 日志,设置合理的堆大小及相关垃圾回收器的参数

5、类和对象跟踪

JVM 提供了一组参数,用于获取系统运行时加载、卸载类的信息,参数设置如下:

-XX:TraceClassLoading:跟踪类加载情况

-XX:TraceClassUnloading:跟踪类的卸载情况

-verbose:class:相当于同时设置 -XX:TraceClassLoading 和 -XX:TraceClassUnloading 两个参数

-XX:+PrintClassHistogram:打印运行时实例的信息,当设置此参数后,使用 Ctrl + Break 会输出系统内类的统计信息,从左到右依次显示了序号、实例数量、总大小和类名等信息

6、控制GC

-XX:DisableExplicitGC:禁止 GC 操作,即禁止在程序中使用 System.gc() 触发 Full GC

-Xnoclassgc:禁止类的回收

-Xingc:增量式的 GC ,增量式的 GC 使用特定的算法让 GC 线程和应用程序线程交叉执行,从而减少应用程序因 GC 产生的停顿时间

-Xverify:none:关闭类校验器

-XX:+UseLargePages:启用大页,使用大页后,内存分页的表项就会减少,从而提升CPU从虚拟内存地址映射到物理内存地址的能力

-XX:LargePageSizeInBytes:指定大页的大小

  • 1
    点赞
  • 17
    收藏
    觉得还不错? 一键收藏
  • 0
    评论

“相关推荐”对你有帮助么?

  • 非常没帮助
  • 没帮助
  • 一般
  • 有帮助
  • 非常有帮助
提交
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值