Java异常的正确使用

我们在写代码的时候 方法或者接口中存在异常时,自己能解决或者调用方根本不关心异常时可以采用try catch方式 而如果存在异常自己无法解决或者调用方需要自己解决的时候 就采用抛异常的方式。

如果我们在项目中随意的处理异常的话会存在什么问题呢?

1.代码可读性变差,业务逻辑难以理解
2.代码健壮性变差,异常信息被随意捕捉,甚至被吃掉
3. 破坏架构的分层清晰,职责单一的原则,为系统扩展带来很大阻碍

如何处理异常

何时抛异常和抛什么异常,何时抓异常和抓什么异常 何时会有异常抛出,总结起来有以下三个典型的场景:

  1. 调用方(Client)破坏了协议

说白了就是调用方法时没有按照约定好的规范来传参数,典型的比如参数是个非空集合却传入了空值。这种破坏协议的还可以细分两类,一类是调用方从接口形式上不易觉察的规则但需要在出现时给调用方些强提示,带些信息上去,这时异常就是特别好的方式;另一类是调用方可以明确看到的规则,正常情况会正常处理协议,不会产生破坏,但可能因为bug导致破坏协议。要求传入整数,但转换数字时出错,此时可抛出特定异常并附上提示信息。

  1. (Method)知道有问题,但自己处理不了

这里"有问题",可能是调用方破坏了协议,但是单独提出来是要从被调用方出发考虑,比如Method内部有读取文件操作,但发现文件并不存在,FileInputStream在创建时抛出了FileNotFoundException,显然出现该问题时FileInputStream是处理不了的。这个时候也是可以抛出去让调用方去try catch 处理。

  1. 预料不到的情形

空指针异常、数组越界是这种典型的场景,一般是由于有代码分支被忽略。

了解了何时会出现异常,但是需要抛出异常时是选择编译时异常还是运行时异常呢? 很多人可能会说,很简单啊,需要调用方catch的就编译时,否则运行时。问题来了,什么时候需要调用方catch?

分析编译时和运行时对代码编写的影响,可以总结出来区分时考虑的点有:调用方能否处理、严重程度、出现的可能性。

  • 调用方能处理 -> 编译时

  • 调用方不能处理 -> 运行时

  • 严重程度高 -> 运行时

  • 出现可能性低 -> 运行时

处理过程

首先从调用方开始考虑,如果是调用方破坏了协议,则抛出运行时异常,这类异常一般出现可能性较低,调用方已知,所以没必要强制调用方抓此异常。

然后如果问题出现被调用方,无法正常执行完成工作,这时候考虑该问题调用方是否可以处理,如果能处理,比如文件找不到、网络超时,则抛出编译时异常,否则比如磁盘满,抛运行时异常。

解决了何时抛异常和抛什么异常,接下来是调用这些有异常的代码时,何时catch和catch什么异常呢? 攻守不分离… 免不了俗,总结一下几点供大家探讨:

不要轻易抓Throwable
图省事可能会带来巨大的隐患应该尽量只去抓关注的异常,明确catch的都是什么具体的异常。

自己处理不了,不要抓
比如上文DB可能会有异常,在DAO层是处理不了这种问题的,交由上层处理。抓异常宜晚不宜早,抛异常宜早不宜迟。

抓了要处理
切忌抓了,又把异常吞掉,不留下一丝痕迹抓住异常,打行日志完事儿,不是一个好习惯。

不要与业务混合
切忌抓异常了将异常状态流和业务状态流混在一起,这样你算是彻底抛弃了Java的异常机制。

  • 0
    点赞
  • 0
    收藏
    觉得还不错? 一键收藏
  • 0
    评论

“相关推荐”对你有帮助么?

  • 非常没帮助
  • 没帮助
  • 一般
  • 有帮助
  • 非常有帮助
提交
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值