Java:异常
·
一、异常整体继承体系(树形结构图)
Throwable (顶层根类)
├─ Error (系统级错误,无法处理)
└─ Exception (程序级异常,可捕获处理)
├─ RuntimeException (运行时异常/非受检异常)
└─ 编译时异常 (受检异常/非运行时异常)
核心概念
- ThrowableJava 中所有异常、错误的最顶层父类,只有它的子类才能被异常处理机制识别。
- Error 错误由 JVM 底层抛出,程序无法捕获、无法修复,属于系统严重故障,只能终止程序。
- Exception 异常由程序逻辑、外部资源问题产生,开发者可以通过代码捕获、处理、恢复程序运行。
二、Exception 详细分类
1. 运行时异常(非受检异常)
- 父类:
RuntimeException - 产生原因:程序员代码逻辑写错
- 特点:编译阶段不报错、不强制处理程序运行时才会崩溃抛出
- 常见类型:
NullPointerException空指针异常ArrayIndexOutOfBoundsException数组下标越界ArithmeticException算术异常(整数除 0)ClassCastException类型强制转换异常
代码示例
public class RuntimeExceptionDemo {
public static void main(String[] args) {
String str = null;
str.length(); // 空指针,运行时报错,编译不报错
}
}
2. 编译时异常(受检异常 / 非运行时异常)
- 不属于
RuntimeException子类 - 产生原因:外部资源问题(文件、网络、IO)
- 特点:编译阶段强制要求处理不写处理代码,直接编译爆红,无法运行
- 常见类型:
FileNotFoundException文件未找到IOExceptionIO 读写异常SQLException数据库操作异常
代码示例
import java.io.FileReader;
public class CheckedExceptionDemo {
public static void main(String[] args) {
// 编译时异常,必须处理,否则编译失败
FileReader fr = new FileReader("a.txt");
}
}
三、Error 常见类型(不可处理)
都是 JVM 级致命错误,不能 try-catch 捕获,只能优化代码:
- StackOverflowError 栈溢出成因:递归没有终止条件、方法无限嵌套调用代码示例:
public class ErrorDemo {
public static void test() {
test(); // 无限递归
}
public static void main(String[] args) {
test();
}
}
- OutOfMemoryError 内存溢出成因:创建过多对象、大集合无限存元素、内存泄漏。
四、异常的两种处理方案
1. try...catch...finally 本地捕获处理
结构作用
try:包裹可能抛出异常的敏感代码catch:捕获对应类型异常,自定义处理逻辑;支持多 catch 分级捕获finally:无论是否出现异常、无论是否 return,一定会执行- 适用场景:关闭 IO 流、数据库连接、释放资源
基础语法 + 多 catch 示例
public class TryCatchDemo {
public static void main(String[] args) {
try {
int a = 1 / 0;
int[] arr = new int[2];
arr[5] = 10;
} catch (ArithmeticException e) {
System.out.println("算术异常:除零错误");
} catch (ArrayIndexOutOfBoundsException e) {
System.out.println("数组越界异常");
} finally {
System.out.println("资源释放,必定执行");
}
}
}
重要规则
finally唯一不执行情况:System.exit(0)直接终止 JVM。
2. throws 声明式抛出异常
- 作用:当前方法不处理异常,把异常抛给调用者处理
- 位置:写在方法签名后面
- 可以一次性抛出多个异常,逗号分隔
- 规则:子类重写父类方法,抛出异常范围不能比父类更大
代码示例:
public class ThrowsDemo {
public static void main(String[] args) throws Exception {
readFile();
}
public static void readFile() throws Exception {
FileReader fr = new FileReader("a.txt");
}
}
五、手动抛出异常:throw
1. 关键字区别
throw:方法内部,主动手动抛出一个异常对象throws:方法声明上,被动声明抛出异常类型
2. 用法示例
public class ThrowDemo {
public static void checkAge(int age) {
if(age < 18){
// 手动抛出异常,自定义提示信息
throw new RuntimeException("年龄未满18,禁止访问");
}
}
public static void main(String[] args) {
checkAge(16);
}
}
六、补充高频必考知识点
- 运行时异常 vs 编译时异常
- 运行时:代码逻辑错,编译不强制处理
- 编译时:外部资源错,编译必须处理
- Error 和 Exception 本质区别
- Error:JVM 系统级错误,不可处理
- Exception:程序业务异常,可捕获恢复
- finally 能不能省略?可以;try 必须搭配 catch 或 finally 至少一个
- e.printStackTrace () 作用打印异常类型、异常信息、代码出错位置,调试必备。
七、终极思维导图(文字版结构图)
Throwable
├─ Error
│ ├─ StackOverflowError 栈溢出
│ └─ OutOfMemoryError 内存溢出
└─ Exception
├─ RuntimeException(运行时异常)
│ ├─ 空指针、数组越界、除零、类型转换
└─ 编译时异常(受检异常)
├─ FileNotFound、IO、SQL异常
更多推荐


所有评论(0)