[读书笔记] 代码整洁之道(三): 错误处理及边界接口处理
第七章 错误处理
这一章并不是给出处理异常的细节,而是从大方向上去告诉我们怎么处理异常才会使得代码看起来可控制。
- 使用异常而非返回码
为什么不使用异常码,且不说你需要定义一个Constant类或者Enum类来保存异常码类别,调用完方法得到返回码后,需要立刻检查错误类型。而在调用方法中遇到错误立刻抛出异常,代码会很整洁。 - 先写Try-Catch-Finally语句
try里面的代码随时会抛出异常,并在catch语句中接续。我们可能不知道会发生什么异常,但是我们可以通过测试一步步缩小异常类型的范围。 - 使用不可控异常
可控异常(checked exception):受检查异常的代价就是违反开放/闭合原则OCP,如果底层函数需要抛出新的可控异常,那么每个调用该函数的函数都需要修改。 - 给出异常发生的环境说明
- 依调用者需要定义异常类
- 定义常规流程
- 别返回null值
一遍遍的检查NullpointException是很繁琐的一件事,可以通过返回空列表进行改进。 - 别传递null值
如果将错误处理隔离看待,独立于主要逻辑之外,就能写出强固而整洁的代码。
第八章 边界
边界就是我们系统中用到的别人的收费或者开源的那部分代码,如果干净利落的讲这些代码整合,而保持软件边界的整洁。
-
使用第三方API
使用第三方提供的函数接口,以java.util.Map为例子,系统中会有大量代码使用Map实体,这意味当Map接口被修改的时候,许多地方都要跟着改。我之前的工作中就遇到这个问题,JDK从1.4升级到1.6之后,代码到处都是黄色的提醒,没有使用泛型。作者提供使用Map更整洁的方式:class Sensors {//将Map封装 private Map sensors = new HashMap(); public Sensor getById(String id) { return (Sensor) sensors.get(id) } } 这样边界接口Map是隐藏的,代码里面收到的影响就会很小。但是不建议总是以这种方式封装Map的使用,建议不要将Map(或边界上的其他接口)在系统中传递。
如果你使用类似Map这样的边界接口,就把他保留在类或亲近类中。避免从公共API中返回边界接口,或将边界接口作为参数传递给公共API。
-
浏览和学习边界
以log4j为例子,当我们需要使用log4j来记录输出的时候,我们一步步调用它提供的方法,直到最后产生输出,我们需要一步步的测试它的代码,这样才可以熟悉log4j的行为,以确保更好更安全的使用log4j. -
学习性测试的好处不只是免费
就像上文里面log4j,我们通过学习性测试了解了log4j的工作方式,以及便于处理log4j修改更新之后是否兼容的问题。 -
使用尚不存在的代码
协同开发过程中经常会碰到代码调用的API还没有处理好的情况,在这中情况下我们定义好我们的接口和方法。一旦API被定义出来,可以使用适配器模式来进行跨接。ADAPTER封装了与API的互动,也提供了一个当API发生变动时唯一需要改动的地方。详细参考设计模式——适配器模式(Coming out...) -
整洁的边界
在我们的代码中应该尽量少的了解第三方代码中的特定信息,也就需要尽量去封装好第三方边界接口。可以像封装Map那样,也可以使用适配器模式将我们的接口转换为第三方的接口。这样当第三方代码改动的时修改点也会更少。