JVM内存溢出的两大类型及解决方案

Posted

tags:

篇首语:本文由小常识网(cha138.com)小编为大家整理,主要介绍了JVM内存溢出的两大类型及解决方案相关的知识,希望对你有一定的参考价值。

参考技术A

  你知道如何解决JVM内存溢出问题吗 这里和大家分享一下 JVM管理两种类型的内存 堆和非堆 堆是给开发人员用的上面说的就是 是在JVM启动时创建 非堆是留给JVM自己用的 用来存放类的信息的

  JVM内存溢出的详细解决方案

  JVM内存溢出类型

   java lang OutOfMemoryError:PermGenspace

  JVM管理两种类型的Java内存 堆和非堆 堆是给开发人员用的上面说的就是 是在JVM启动时创建 非堆是留给JVM自己用的 用来存放类的信息的 它和堆不同 运行期内GC不会释放空间 如果webapp用了大量的第三方jar或者应用有太多的class文件而恰好MaxPermSize设置较小 超出了也会导致这块内存的占用过多造成JVM内存溢出 或者tomcat热部署时侯不会清理前面加载的环境 只会将context更改为新部署的 非堆存的内容就会越来越多

  PermGenspace的全称是PermanentGenerationspace 是指内存的永久保存区域 这块内存主要是被JVM存放Class和Meta信息的 Class在被Loader时就会被放到PermGenspace中 它和存放类实例(Instance)的Heap区域不同 GC(GarbageCollection)不会在主程序运行期对PermGenspace进行清理 所以如果你的应用中有很CLASS的话 就很可能出现PermGenspace错误 这种错误常见在web服务器对JSP进行prepile的时候 如果你的WEBAPP下都用了大量的第三方jar 其大小超过了jvm默认的大小( M)那么就会产生此错误信息了

  一个最佳的配置例子 (经过本人验证 自从用此配置之后 再未出现过tomcat死掉的情况)

   setJAVA_OPTS= Xms m

   Xmx m XX:PermSize= M

   XX:MaxNewSize= m

   XX:MaxPermSize= m

   java lang OutOfMemoryError:Javaheapspace

  再来看一下JVM内存溢出的第二种情况 第一种情况是个补充 主要存在问题就是出现在这个情况中 其默认空间(即 Xms)是物理内存的 / 最大空间( Xmx)是物理内存的 / 如果内存剩余不到 % JVM就会增大堆到Xmx设置的值 内存剩余超过 % JVM就会减小堆到Xms设置的值 所以服务器的Xmx和Xms设置一般应该设置相同避免每次GC后都要调整虚拟机堆的大小 假设物理内存无限大 那么JVM内存的最大值跟操作系统有关 一般 位机是 g到 g之间 而 位的就不会有限制了

  注意 如果Xms超过了Xmx值 或者堆最大值和非堆最大值的总和超过了物理内存或者操作系统的最大限制都会引起服务器启动不起来

  垃圾回收GC的角色

  JVM调用GC的频度还是很高的 主要两种情况下进行垃圾回收

  当应用程序线程空闲 另一个是java内存堆不足时 会不断调用GC 若连续回收都解决不了内存堆不足的问题时 就会报outofmemory错误 因为这个异常根据系统运行环境决定 所以无法预期它何时出现 根据GC的机制 程序的运行会引起系统运行环境的变化 增加GC的触发机会

lishixinzhi/Article/program/Java/hx/201311/26579

几种内存溢出的类型及解决思路

相信有一定java开发经验的人或多或少都会遇到OutOfMemoryError的问题,这个问题曾困扰了我很长时间,随着解决各类问题经验的积累以及对问题根源的探索,终于有了一个比较深入的认识。 在解决java内存溢出问题之前,需要对jvm(java虚拟机)的内存管理有一定的认识。jvm管理的内存大致包括三种不同类型的内存区域:Permanent Generation space(永久保存区域)、Heap space(堆区域)、Java Stacks(Java栈)。其中永久保存区域主要存放Class(类)和Meta的信息,Class第一次被Load的时候被放入PermGen space区域,Class需要存储的内容主要包括方法和静态属性。堆区域用来存放Class的实例(即对象),对象需要存储的内容主要是非静态属性。每次用new创建一个对象实例后,对象实例存储在堆区域中,这部分空间也被jvm的垃圾回收机制管理。而Java栈跟大多数编程语言包括汇编语言的栈功能相似,主要基本类型变量以及方法的输入输出参数。Java程序的每个线程中都有一个独立的堆栈。容易发生内存溢出问题的内存空间包括:Permanent Generation space和Heap space。
第一种OutOfMemoryError: PermGen space 发生这种问题的原意是程序中使用了大量的jar或class,使java虚拟机装载类的空间不够,与Permanent Generation space有关。解决这类问题有以下两种办法: 1. 增加java虚拟机中的XX:PermSize和XX:MaxPermSize参数的大小,其中XX:PermSize是初始永久保存区域大小,XX:MaxPermSize是最大永久保存区域大小。如针对tomcat6.0,在catalina.sh 或catalina.bat文件中一系列环境变量名说明结束处(大约在70行左右) 增加一行: JAVA_OPTS=" -XX:PermSize=64M -XX:MaxPermSize=128m" 如果是windows服务器还可以在系统环境变量中设置。感觉用tomcat发布sprint+struts+hibernate架构的程序时很容易发生这种内存溢出错误。使用上述方法,我成功解决了部署ssh项目的tomcat服务器经常宕机的问题。 2. 清理应用程序中web-inf/lib下的jar,如果tomcat部署了多个应用,很多应用都使用了相同的jar,可以将共同的jar移到tomcat共同的lib下,减少类的重复加载。这种方法是网上部分人推荐的,我没试过,但感觉减少不了太大的空间,最靠谱的还是第一种方法。
第二种OutOfMemoryError:  Java heap space 发生这种问题的原因是java虚拟机创建的对象太多,在进行垃圾回收之间,虚拟机分配的到堆内存空间已经用满了,与Heap space有关。解决这类问题有两种思路: 1. 检查程序,看是否有死循环或不必要地重复创建大量对象。找到原因后,修改程序和算法。 我以前写一个使用K-Means文本聚类算法对几万条文本记录(每条记录的特征向量大约10来个)进行文本聚类时,由于程序细节上有问题,就导致了Java heap space的内存溢出问题,后来通过修改程序得到了解决。 2. 增加Java虚拟机中Xms(初始堆大小)和Xmx(最大堆大小)参数的大小。如:set JAVA_OPTS= -Xms256m -Xmx1024m
第三种OutOfMemoryError:unable to create new native thread 这种错误在Java线程个数很多的情况下容易发生

以上是关于JVM内存溢出的两大类型及解决方案的主要内容,如果未能解决你的问题,请参考以下文章

关于JVM内存溢出的原因分析及解决方案探讨

Tomcat中JVM内存溢出及合理配置

tomcat编译内存溢出怎么解决

Tomcat中JVM内存溢出及合理配置

Java中OutOfMemoryError(内存溢出)的三种情况及解决办法

JVM内存溢出及配置