星海

JVM · 主观题 · 第 31 题

Java 后端开发面试 · 第 31 题

JVM 运行时数据区是如何划分的?哪些区域可能发生 OOM?

参考答案

1. 线程私有:程序计数器(唯一不会 OOM 的区域);虚拟机栈(栈帧里有局部变量表、操作数栈等,递归过深抛 StackOverflowError,无法再创建线程时可能 OOM);本地方法栈。
2. 线程共享:堆(对象实例和数组,GC 的主要区域,分新生代和老年代,满了抛 OutOfMemoryError: Java heap space);方法区,JDK 8 起由元空间实现,使用本地内存,存类元数据,满了抛 OutOfMemoryError: Metaspace。
3. 运行时常量池属于方法区;字符串常量池和静态变量从 JDK 7 起移到了堆中。
4. 直接内存不属于运行时数据区,NIO 的 DirectByteBuffer 使用它,受 -XX:MaxDirectMemorySize 限制,不足时抛 OutOfMemoryError: Direct buffer memory。
5. 排查 OOM:加 -XX:+HeapDumpOnOutOfMemoryError 导出堆快照,用 MAT 等工具看占用最大的对象和它们的引用链。

解析

按线程私有和共享分类,并说明各自的异常类型。

在线刷这套题:即时判分、错题本、闪卡复习,不用登录就能练。