关键在于责任归属:受检异常用于外部可恢复的不确定性(如io异常),需调用方处理;运行时异常用于内部逻辑缺陷(如空指针、非法参数),应在开发阶段拦截;各层按职责封装异常,底层转业务运行时异常,应用层抛语义化自定义异常。

关键不在“抛什么异常”,而在于“谁该为这件事负责”。选型本质是契约设计——告诉调用方:这个问题你必须处理,还是我代码写错了该自己修。
看问题来源:外部不确定性 vs 内部逻辑缺陷
受检异常适合描述程序无法控制、但业务上可预期且能恢复的外部状况。比如文件读取失败(磁盘损坏)、数据库连接超时(网络抖动)、支付回调验签失败(第三方服务临时异常)。这些不是 bug,而是现实环境的一部分,调用方理应有应对策略。
运行时异常则指向代码自身问题:没判空就调用方法、传了非法状态码、循环边界算错、参数明显违反前置条件(如年龄传 -5)。这类问题不该靠 catch 补救,而应在入口校验、单元测试、Code Review 阶段拦截。
- 用户上传文件 → 可能不存在或权限不足 → IOException(受检),让 Controller 决定返回 404 还是重试
- 用户提交订单时传了 null 的收货地址 → IllegalArgumentException(运行时),API 入口就该拦住并返回 400
- 库存扣减时发现 DB 更新行数为 0 → InsufficientStockException(自定义运行时),这是业务规则失败,不是系统意外
看分层职责:基础设施封装,应用层表达语义
底层技术组件(JDBC、HTTP Client、文件系统)抛出的原始受检异常(如 SQLException、IOException),不应直接暴露给上层。应在 DAO 或 Client 层统一转换为带业务上下文的运行时异常,例如 DataAccessException、RemoteServiceException。
应用服务层(Service)聚焦业务规则,抛出自定义运行时异常,名称直指业务含义:“余额不足”“活动已结束”“重复提交”。这些异常不强制调用方处理,但 Controller 层会统一捕获,转为标准错误响应(含 code、message、traceId)。
- DAO 层:catch SQLException → throw new DataAccessException("扣减库存失败", e)
- Service 层:if (balance
- Controller 层:@ExceptionHandler(InsufficientBalanceException.class) → 返回 { "code": "BALANCE_INSUFFICIENT", "msg": "余额不足" }
看调用方角色:内部协作 vs 对外 SDK
同一项目内模块间调用,优先用运行时异常。它不污染方法签名,避免每层都 throws,也避免调用方写一堆无意义的 try-catch。
但当你提供开放 SDK 给第三方,或在强一致性金融流程中(如资金冻结后必须确认到账),受检异常就有价值:它强制对方意识到“这事可能失败,你得写逻辑处理”。比如 PaymentTimeoutException、CertificateExpiredException,明确要求调用方实现超时重试或人工介入分支。
- 公司内部订单服务调用库存服务 → 库存不足抛 RuntimeException → 调用方按需处理,不强制
- 对外提供的「电子发票开具 SDK」→ 开票失败抛 InvoiceGenerationException(受检)→ 强制集成方决定是重试、降级为 PDF,还是告警人工处理
看异常命名与继承:别被名字骗,只看父类
判断依据永远是继承关系,不是异常名。UnsupportedEncodingException 听起来像错误,但它继承 IOException → 受检;你自己写的 BusinessException extends RuntimeException → 就是运行时,哪怕叫 “BusinessException” 也一样。
IDE 里按 Ctrl/Cmd 点进异常类,一眼就能看到 extends 谁。编译器反馈最直接:写一行 new FileInputStream("x.txt") 不加处理,编译报错 → 受检;写 String s = null; s.length() 编译通过 → 运行时。
- 查源码:public class MyBizException extends RuntimeException → 运行时异常
- 查源码:public class ConfigLoadException extends Exception → 受检异常
- 编译验证:不处理就过不了编译 → 必须显式应对 → 受检
Java免费学习笔记:立即使用
解锁 Java 大师之旅:从入门到精通的终极指南











