目录
一、概念
栈溢出(StackOverflowError)
概念: 栈溢出是指线程的调用栈(即方法调用的嵌套)超过了系统所允许的最大深度,导致栈溢出异常。在Java中,每个线程都有一个调用栈,用于存储方法调用的信息。
常见原因:
- 递归调用深度过大,没有合适的终止条件。
- 方法调用层次过多,导致栈空间耗尽。
堆溢出(OutOfMemoryError)
概念: 堆溢出是指Java虚拟机中的堆内存不足以支持新的对象创建时抛出的异常。在Java中,堆用于存储对象实例。
常见原因:
- 内存泄漏,无法被垃圾回收的对象持续占用堆内存。
- 创建大量对象,导致堆内存不足。
二、排查方法
栈溢出(StackOverflowError)
排查方法:
-
检查递归: 检查代码中的递归调用,确保终止条件的设置是正确的。
-
减少递归深度: 如果是合理的递归,可以尝试减少递归的深度,或者改用循环来代替递归。
-
增加栈大小: 通过调整虚拟机参数
-Xss
来增加线程的栈大小。例如:java -Xss2m YourClassName
堆溢出(OutOfMemoryError)
排查方法:
-
使用内存分析工具: 如 VisualVM、MAT 等工具,观察堆内存使用情况,找出内存泄漏的地方。
-
检查代码: 仔细检查代码,确保不再使用的对象能够被及时垃圾回收。
-
调整堆大小: 通过虚拟机参数
-Xmx
来增加堆的最大容量。例如:java -Xmx512m YourClassName
4.优化代码: 减少对象的创建,尽可能重用对象,优化集合的使用等。
相关的Java代码示例
栈溢出
public class StackOverflowExample {
public static void main(String[] args) {
stackOverflowMethod(0);
}
private static void stackOverflowMethod(int count) {
// Recursive method without a proper termination condition
stackOverflowMethod(count + 1);
}
}

堆溢出
import java.util.ArrayList;
import java.util.List;
public class HeapOverflowExample {
public static void main(String[] args) {
List<Object> list = new ArrayList<>();
while (true) {
// Creating a large number of objects to fill up the heap
list.add(new Object());
}
}
}