【发布时间】:2016-08-06 03:24:11
【问题描述】:
我正在使用 Java 8 Stream API,我们知道它不支持 java.util.function 内任何功能接口内的检查异常。
我通常必须在流操作中使用带有检查异常的方法,并且我已经编写了 CheckedFunction 装饰器以在这些操作中使用:
import java.util.function.BiFunction;
import java.util.function.Function;
public interface CheckedFunction<T, R, E extends Throwable> {
R apply(T t) throws E;
static <T, R, CE extends Throwable, UCE extends RuntimeException> Function<T, R> checked(
CheckedFunction<T, R, CE> checked, Function<CE, UCE> exceptionHandler) {
return (t) -> {
try {
return checked.apply(t);
}
catch (RuntimeException | Error e) {
throw e;
}
catch (Throwable e) {
// can't catch - compiler error
if (e instanceof InterruptedException) {
Thread.currentThread().interrupt();
}
throw exceptionHandler.apply((CE) e);
}
};
}
}
所以我可以在这种情况下使用它:
entities.stream()
.map(checked((entity) -> someResultChecked(entity), // throws IOException
(entity, e) -> { // e is of type IOException
log.error("exception during checked method of " + entity, e);
return new UncheckedIOException(e);
}))
.map(checked((entity) -> saveToDb(entity), // throws SQLException
(entity, e) -> { // e is of type SQLException
log.error("exception during saving " + entity, e);
return new UncheckedSQLException(e);
}))
.map(checked((entity) -> manyExceptionMethod(entity), // throws IOException, SQLException
(entity, e) -> { // e is of type Throwable
return new RuntimeException(e);
}))
它将任何已检查的异常包装为未检查的,但我知道如果方法抛出多个异常,它将擦除到 Throwable,我将在简单的情况下使用它。
这是个好主意,还是我会遇到隐藏的障碍?
更新:重新抛出 RuntimeExceptions。
我还在 jOOL 中找到了更清晰的解决方案,处理 InterruptedException 如果将被忽略,可能会导致不一致的行为: https://github.com/jOOQ/jOOL/blob/master/src/main/java/org/jooq/lambda/Unchecked.java
【问题讨论】:
-
你应该看看 JavaRx,它提供了一个很好的 API 用于错误处理的流媒体
-
谢谢,我试了好几次,但总是放弃。也许这是我需要整理的信号。
标签: java function exception lambda java-stream