Java 常见的几种JVM内存溢出及解决方法

Java 常见的几种JVM内存溢出及解决方法

【情况一】:
java.lang.OutOfMemoryError:Javaheapspace:这种是 java 堆内存不够,一个原因是真不够(如递归的层数太多等),另一个原因是程序中有死循环;
如果是 java 堆内存不够的话,可以通过调整 JVM 下面的配置来解决:
-Xms3072m
-Xmx3072m
【情况二】:
java.lang.OutOfMemoryError:GCoverheadlimitexceeded
【解释】:JDK6 新增错误类型,当 GC 为释放很小空间占用大量时间时抛出;一般是因为堆太小,导致异常的原因,没有足够的内存。
【解决方案】:
1、查看系统是否有使用大内存的代码或死循环;
2、通过添加 JVM 配置,来限制使用内存:
-XX:-UseGCOverheadLimit
【情况三】:
java.lang.OutOfMemoryError:PermGenspace:这种是 P 区内存不够,可通过调整 JVM 的配置:
-XX:MaxPermSize=128m
-XXermSize=128m
【注】:
JVM 的 Perm 区主要用于存放 Class 和 Meta 信息的,Class 在被 Loader 时就会被放到 PermGenspace,这个区域成为年老代,GC 在主程序运行期间不会对年老区进行清理,默认是 64M 大小,当程序需要加载的对象比较多时,超过 64M 就会报这部分内存溢出了,需要加大内存分配,一般 128m 足够。
【情况四】:
java.lang.OutOfMemoryError:Directbuffermemory
调整 - XX:MaxDirectMemorySize = 参数,如添加 JVM 配置:
-XX:MaxDirectMemorySize=128m
【情况五】:
java.lang.OutOfMemoryError:unabletocreatenewnativethread
【原因】:Stack 空间不足以创建额外的线程,要么是创建的线程过多,要么是 Stack 空间确实小了。
【解决】:由于 JVM 没有提供参数设置总的 stack 空间大小,但可以设置单个线程栈的大小;而系统的用户空间一共是 3G,除了 Text/Data/BSS/MemoryMapping 几个段之外,Heap 和 Stack 空间的总量有限,是此消彼长的。因此遇到这个错误,可以通过两个途径解决:1. 通过 - Xss 启动参数减少单个线程栈大小,这样便能开更多线程(当然不能太小,太小会出现 StackOverflowError);2. 通过 - Xms-Xmx 两参数减少 Heap 大小,将内存让给 Stack(前提是保证 Heap 空间够用)。
【情况六】:
java.lang.StackOverflowError
【原因】:这也内存溢出错误的一种,即线程栈的溢出,要么是方法调用层次过多(比如存在无限递归调用),要么是线程栈太小。
【解决】:优化程序设计,减少方法调用层次;调整 - Xss 参数增加线程栈大小。

-------------本文结束感谢您的阅读-------------