JVM——堆内存调优(Jprofiler使用)Jprofile下载和安装很容易,故没有记录,如有需要,在评论区留言)

堆内存调优

当遇到OOM时,可以进行调参

1、尝试扩大堆内存看结果

2、分析内存,看哪个地方出现了问题(专业工具)

调整初始分配内存为1024M,调整最大分配内存为1024M,打印GC细节(如何添加JVM操作往下看)

-Xms1024m -Xmx1024m -XX:+PrintFGCDetails

在一个项目中,突然出现了OOM故障,那么该如何排除,研究为什么出错

  • 能够看到代码第几行出错:内存快照分析工具,MAT,Jprofiler
  • Dubug,一行行分析代码

MAT,Jprofiler作用:

  • 分析Dump内存文件,快速定位内存泄露;
  • 获得堆中的数据
  • 获得大的对象

下面是一个使用Jprofile查OOM来源的示例

(已经下载好了Jprofile以及Idea插件)

首先写一个必定会OOM的代码:

import java.util.ArrayList;


public class Demo {

    byte[] array = new byte[1*1024*1024];//1m

    public static void main(String[] args) {

        ArrayList<Demo> list = new ArrayList<>();
        int count = 0;

        try{
            while(true){
                list.add(new Demo());
                count = count + 1;
            }
        }catch (Exception e){

        }

    }
}

该问题会虽然用try-catch尝试捕获异常,但问题是,OOM是Error,而非Exception,因此无法排查错误。

首先:

在这里插入图片描述

我们需要添加一些JVM的操作,以至于我们可以在程序运行后在终端查询到JVM的反馈

1、添加JVM操作

在这里插入图片描述

2、添加JVM操作栏(该IDE版本为2023版,因此许多UI做出了修改,与狂神说的UI不同)

在这里插入图片描述

3、在VM option内写下: -Xms1m -Xmx8m -XX:+HeapDumpOnOutOfMemoryError意思为:限制初始化堆内存大小为1M,最大堆内存为8M,Dump出OOM

在这里插入图片描述

接下来运行程序,终端会给出JVM信息,下列信息中,第一行表示出现OOM,位置在HeapSpace,即堆空间。第二行表示已经将堆dump出一个.hprof文件,名字为java_pid44260,你可以在文件夹中找到它,也可以直接在project中找到它

在这里插入图片描述

可以发现,除了java_pin44260.hprof文件外,还dump出了一个文件夹,这个文件夹中包含了大量信息,十分占用空间,如果排查完错误,记得删除。

在这里插入图片描述

点开java_pin44260.hprof,如果安装好Jprofile,则会直接跳转到Jprofile,这里可以看到各类占用的空间大小

在这里插入图片描述

跳到Biggest Objects,可以看到,大部分的内存都是由ArrayList构成的,且可以看到它的类型为byte[],现在我们里真相很近了!

在这里插入图片描述

点击Thread Dump,查看线程Dump,因为示例中并没有开多线程,因此问题大概率是出现在main线程中,天使线程大概率是不会出现问题的,所以直接查main,我们可以发现,main线程中发现了OOM,且给出了具体位置具体行数,

在这里插入图片描述

点进去,即可直接跳转到相应位置,我们发现,它直接跳到Demo.java中,光标停留在main方法上,说明问题在此,并且Jprofile给出了具体行数,17行,因此我们就可以锁定问题所在了,就在这!

import java.util.ArrayList;


// Dump文件
public class Demo {

    // -Xms1m -Xmx8m -XX:+HeapDumpOnOutOfMemoryError
    byte[] array = new byte[1*1024*1024];//1m

    public static void main(String[] args) {

        ArrayList<Demo> list = new ArrayList<>();
        int count = 0;

        try{
            while(true){
//------------------------------------------------------------------
                list.add(new Demo());//问题所在!!!!!!!!!!!
//------------------------------------------------------------------
                count = count + 1;
            }
        }catch (Exception e){

        }

    }
}

  • 6
    点赞
  • 1
    收藏
    觉得还不错? 一键收藏
  • 打赏
    打赏
  • 0
    评论
Tomcat 是一个基于 Java 的 Web 服务器,它运行在 JVM 上。因此,对 Tomcat 进行堆内存调优需要同时考虑 JVM 的内存设置和 Tomcat 的 JVM 参数设置。 以下是一些常用的堆内存调优参数,可以在 Tomcat 配置文件中进行设置: 1. -Xms 和 -Xmx 参数 这两个参数分别代表 JVM 堆的最小值和最大值。建议将它们设置为相同的值,以避免 JVM 在运行时动态调整堆大小导致性能下降。 例如,将 Tomcat 的启动脚本中的 -Xms 和 -Xmx 设置为 2GB: ``` JAVA_OPTS="-Xms2g -Xmx2g" ``` 2. -XX:NewSize 和 -XX:MaxNewSize 参数 这两个参数分别代表新生代的最小值和最大值。新生代一般占据 JVM 堆的比例较小,因此可以设置较小的值。 例如,将 Tomcat 的启动脚本中的 -XX:NewSize 和 -XX:MaxNewSize 设置为 256MB: ``` JAVA_OPTS="-XX:NewSize=256m -XX:MaxNewSize=256m" ``` 3. -XX:SurvivorRatio 参数 这个参数用于设置 Eden 和 Survivor 的比例。一般来说,Survivor 的大小应该是 Eden 的 1/3 到 1/4。 例如,将 Tomcat 的启动脚本中的 -XX:SurvivorRatio 设置为 4: ``` JAVA_OPTS="-XX:SurvivorRatio=4" ``` 4. -XX:MaxTenuringThreshold 参数 这个参数用于设置对象进入老年代的年龄阈值。一般建议将它设置为 15。 例如,将 Tomcat 的启动脚本中的 -XX:MaxTenuringThreshold 设置为 15: ``` JAVA_OPTS="-XX:MaxTenuringThreshold=15" ``` 5. -XX:+UseConcMarkSweepGC 和 -XX:+UseParNewGC 参数 这两个参数分别代表使用 CMS 垃圾回收器和使用 ParNew 垃圾回收器。CMS 垃圾回收器适用于多核 CPU,能够在不中断应用程序的情况下进行垃圾回收;ParNew 垃圾回收器适用于单核 CPU,能够加速新生代的垃圾回收。 例如,将 Tomcat 的启动脚本中的 -XX:+UseConcMarkSweepGC 和 -XX:+UseParNewGC 设置为 true: ``` JAVA_OPTS="-XX:+UseConcMarkSweepGC -XX:+UseParNewGC" ``` 以上是一些常用的堆内存调优参数,可以根据实际情况进行调整。同时,建议使用 JVM 监控工具如 JConsole 和 VisualVM 来监控 JVM 的内存使用情况,及时调整参数以达到最优化的性能。

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

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

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包

打赏作者

苏三有春

你的鼓励将是我创作的最大动力

¥1 ¥2 ¥4 ¥6 ¥10 ¥20
扫码支付:¥1
获取中
扫码支付

您的余额不足,请更换扫码支付或充值

打赏作者

实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

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

余额充值