什么是OOM
先简单的谈一谈什么是OOM,全写就是(OutOdMemoryError),就是我们的堆内存不够而出现的错误
首先错误和异常是有区别的,程序运行时有些异常是我们可以通过异常处理去处理的,不影响我们程序的运行,但是出现错误的话我们的程序会立马中断。
出现OOM的原因以及分析
当我们去在堆中创建对象过多且都去频繁使用的时候GC帮我们清理不过来的时候就可能把堆内存打满,我们下边去看一段代码
public class Test {
byte[] array = new byte[1 * 1024 * 1024];
public static void main(String[] args) {
ArrayList<Object> list = new ArrayList<>();
int count = 0;
try {
while (true) {//在这无线循环去new对象
list.add(new Test());
count++;
}
} catch (OutOfMemoryError e) {
System.out.println("count" + count);
e.printStackTrace();
}
}
}
执行代码的结果
java.lang.OutOfMemoryError: Java heap space
当然为了避免我们的电脑风扇cilacila的转,我们在执行代码前去加一行参数
-Xms1m -Xmx8m -XX:+HeapDumpOnOutOfMemoryError 加这行参数有什么作用呢?
Xms 设置初始化内存大小 1/64
Xmx 设置最大内存大小 1/4
-XX:PrintGCDetails 打印GC垃圾回收信息
-XX:+HeapDumpOnOutOfMemoryError 当内存溢出时获取Dump文件
Dump文件在哪里找呢?
运行之后去我们项目目录下
会发现一个这样的文件
分析Dump文件
1、Idea中下载分析插件
2、Jprofiler软件安装
下载好之后我们也需要去下载Jprofiler这个软件
官网下载地址
下载好直接一路next就完事了
3、配置连接
在idea中找到我们的JProfiler然后右边设置到我们下载好的bin/目录下的.exe文件点击Apply 然后OK就好了
4、双击打开
打开之后可以看到我们内存的使用情况
这里也可以看到详细信息,那么怎么定位报错呢?
5、定位报错
可以点击Thread Dump 看到我们当前运行线程,找到我们的main线程 然后下边可以看出来我们错误在29行,接下来看一下我们代码的29行
的确可以看出来是我们这行往堆中创建对象的时候报错了!!这样在复杂的情况下我们就不需要一步一步Debug去调试代码找错误了,通过分析内存快照(Dump文件)就可以精准的定位我们的错误!
你学废了嘛?