运行时数据区域

image.png


HotSpot虚拟机对象操作

image.png


OutOfMemoryError异常

image.png
异常这一块还有待完善,后面进一步了解垃圾回收机制,进行内存异常排查时再补充

Java堆内存溢出异常测试

  1. import java.util.ArrayList;
  2. import java.util.List;
  3. /**
  4. * VM options: -Xms20m -Xmx20m -XX:+HeapDumpOnOutOfMemoryError -XX:HeapDumpPath=/Users/.../java_oom
  5. */
  6. public class HeapOOM {
  7. static class OOMObject {
  8. }
  9. public static void main(String[] args) {
  10. List<OOMObject> list = new ArrayList<OOMObject>();
  11. while (true) {
  12. list.add(new OOMObject());
  13. }
  14. }
  15. }
  16. /* 抛错打印
  17. java.lang.OutOfMemoryError: Java heap space
  18. Dumping heap to /User/.../java_oom/java_pid11783.hprof ...
  19. Heap dump file created [28524065 bytes in 0.116 secs]
  20. Exception in thread "main" java.lang.OutOfMemoryError: Java heap space
  21. at java.util.Arrays.copyOf(Arrays.java:3210)
  22. at java.util.Arrays.copyOf(Arrays.java:3181)
  23. at java.util.ArrayList.grow(ArrayList.java:265)
  24. at java.util.ArrayList.ensureExplicitCapacity(ArrayList.java:239)
  25. at java.util.ArrayList.ensureCapacityInternal(ArrayList.java:231)
  26. at java.util.ArrayList.add(ArrayList.java:462)
  27. at com.guorou.sell.activity.HeapOOM.main(HeapOOM.java:18)
  28. */

提问环节

  1. HotSpot虚拟机中,将永久代废弃后,之前存储在永久代的内容现在放到哪儿了?
    1. HotSpot在JDK8彻底废弃永久代后,取而代之的是使用元空间
    2. 元空间也是在方法区实现的,和永久代最大差别是它不在虚拟机中,而是使用本地内存
    3. 而废弃永久代的理由主要是两方面:
      • 这个设计之前是为了偷懒,省去在方法区开发内存管理,结果就是这一块的内存非常容易溢出
      • 因为收购了JRockit、J9(这两个就是用了元空间来实现方法区),所以采用和它们一样的实现方式,算是一个优化
    4. 参考:JVM废弃永久代
  2. Java虚拟机最常用的参数介绍?分别代表什么含义? | 参数设置 | 描述 | 配置格式 | | —- | —- | —- | | -Xms | 初始化堆空间大小 | -Xms64m | | -Xmx | 最大堆空间大小 | -Xmx128m | | -Xmn | 年轻代的空间大小 | -Xmn32m | | -Xss | 设置线程栈空间大小 | -Xss512k | | -XX:PermSize | 永久代空间大小(jdk8已废弃) | -XX:PermSize=256m | | -XX:MaxPermSize | 最大永久区大小 | -XX:MaxPermSize=256m | | -XX:+UseStringCache | 启用缓存常用字符产 | | | -XX:+UseConcMarkSweepGC | 老年代使用cms收集器 | | | -XX:+UseParNewGC | 新生代使用并行收集器 | | | -XX:+ParallelGCThreads | 设置并行线程数量 | -XX:+ParallelGCThreads=4 | | -XX:+CMSClassUnloadingEnabaled | 允许对类元数据进行清理 | | | -XX:+DisableExplicitGC | 禁止显示GC | | | -XX:+UseCMSInitiatingOccupancyOnly | 表示达到阀值之后才进行CMS回收 | | | -XX:+CMSInitiatingOccupanyFraction | 设置CMS老年代回收阀值百分比 | -XX:+CMSInitiatingOccupanyFraction=68 | | -verbose:gc | 输出虚拟机GC详情 | | | -XX:+PrintGCDetails | 打印GC详情 | | | -XX:+PrintGCDateStamps | 打印GC的耗时 | | | -XX:+PrintTenuringDistribution | 打印tenuring年龄信息 | | | -XX:+HeapDumpOnOutOfMemoryError | 当抛出OOM时进行HeapDump | - | | -XX:+HeapDumpPath | 指定HeapDump的文件路径和目录 | - |