Preconditions作为Guava中异常的前置检查,提供了一系列方法。从源码的实现中可以看出,所有的方法都满足以下形式(除format()方法以外)。
if (!status) { throw new xxException(); }
例如:
public static void checkArgument(boolean expression) { if (!expression) { throw new IllegalArgumentException(); } }
源码实现比较简单,没有太多需要细说。其中有个方法,format()方法,不同于String.format(),源码实现如下:
static String format(String template, @Nullable Object... args) { template = String.valueOf(template); // null -> "null" // start substituting the arguments into the '%s' placeholders StringBuilder builder = new StringBuilder(template.length() + 16 * args.length); int templateStart = 0; int i = 0; while (i < args.length) { int placeholderStart = template.indexOf("%s", templateStart); if (placeholderStart == -1) { break; } builder.append(template.substring(templateStart, placeholderStart));// 获取%s之前的字符串进行拼接 builder.append(args[i++]);//替换%s templateStart = placeholderStart + 2; } builder.append(template.substring(templateStart));//拼接之后的字符串
// 如果还有为使用的args。直接在[]内显示出来 // if we run out of placeholders, append the extra args in square braces if (i < args.length) { builder.append(" ["); builder.append(args[i++]); while (i < args.length) { builder.append(", "); builder.append(args[i++]); } builder.append(']'); } return builder.toString();
与Preconditions类似的功能类,Verify提供了类似的方法,JDK原生的Assert也提供了类似的方法,使用方式遵循一下原则
- Precondis用于API实现者检查API参数的合法性,语义为"你弄的一团糟(API调用者)"
- Verify一般用于API实现者,在实现自己API的时候,调用其他API时,验证其返回的结果是否被期望,语义为"一些我依赖的东西弄糟了一切"
- Assert一般用于Junit中,断言测试是否成功
《Effective Java》中58条对CheckedException、RuntimeException和Error使用方式做了详细的说明:
- CheckedException用于开发人员,在catch到Exception后,可以尝试解决的场景。
- RuntimeException用于代表程序逻辑异常,但是此异常不可恢复,可根据程序逻辑,自定义(继承RuntimeException)。
- Error与RuntimeException的应用场景差不多,但是不要尝试去继承Error,会使得程序语义混乱,使用JDK原生Error就好。