Lombok基本注解之@SneakyThrows的作用
@SneakyThrows注解是由lombok封装的,为代码生成一个try…catch块,并把异常向上抛出来
使用范围: 只能作用在方法和构造函数之上。
而java中常见的异常有两种:
Exception即非运行时异常(编译异常)。
RuntimeException即运行时异常。
然而程序员大部分情况下,处理Exception的常见手段就是外面包一层RuntimeException,接着往上抛(throws Exception)。
try {
int userId = user.getId();
} catch (Exception e) {
throw new RuntimeException(e);
}
Lombok的@SneakyThrows就是为了消除这样的模板代码。
使用注解后不需要担心Exception的处理
@SneakyThrows
public void login(User user){
int userId = user.getId();
}
编译器生成真正的代码:
public void login(User user){
try {
int userId = user.getId();
} catch (Exception e) {
throw Lombok.sneakyThrow(e);
}
}
原理:
阅读源码可以看出整个方法其实最核心的逻辑是throw (T)t;,利用泛型将我们传入的Throwable强转为RuntimeException。虽然事实上我们不是RuntimeException。但是没关系。因为JVM并不关心这个。泛型最后存储为字节码时并没有泛型的信息。这样写只是为了骗过javac编译器。源码中注释有解释。
public static RuntimeException sneakyThrow(Throwable t) {
if (t == null) throw new NullPointerException("t");
return Lombok.<RuntimeException>sneakyThrow0(t);
}
private static <T extends Throwable> T sneakyThrow0(Throwable t) throws T {
throw (T)t;
}