java - 处理 Java8 流中的已检查异常
问题描述
假设您有一个公开下一个接口的 3rd 方库。
interface Mapper {
String doMap(String input) throws CheckedException;
}
class CheckedException extends Exception {
}
我知道检查异常在 Java 中通常是一种不好的做法,但是这段代码来自第 3 方,我无法修改它。
我想结合 Java8 流 API 使用 Mapper 接口的实现。考虑下面的示例实现。
class MapperImpl implements Mapper {
public String doMap(String input) throws CheckedException {
return input;
}
}
现在,例如,我想将映射器应用于字符串集合。
public static void main(String[] args) {
List<String> strings = Arrays.asList("foo", "bar", "baz");
Mapper mapper = new MapperImpl();
List<String> mappedStrings = strings
.stream()
.map(mapper::doMap)
.collect(Collectors.toList());
}
代码无法编译,因为 Function 不知道如何处理 doMap 声明的 CheckedException。我想出了两种可能的解决方案。
解决方案 #1 - 包装调用
.map(value -> {
try {
return mapper.doMap(value);
} catch (CheckedException e) {
throw new UncheckedException();
}
})
解决方案 #2 - 编写实用程序方法
public static final String uncheck (Mapper mapper, String input){
try {
return mapper.doMap(input);
} catch (CheckedException e){
throw new UncheckedException();
}
}
然后我可以使用
.map(value -> Utils.uncheck(mapper, value))
在您看来,在 Java8 流的上下文中(以及在更广泛的 lambda 表达式的上下文中)处理检查异常的最佳方法是什么?
谢谢!
解决方案
您基本上列出了两个可行的选项。
另一种选择是将检查的异常从流处理函数中抛出(“传播”或“潜入”检查的异常)。这是通过捕获已检查异常并将其重新抛出RuntimeException
(通过强制转换)来完成的。看看这个很好的答案了解详情。
已经开发了多个库来处理流 API 中的异常处理。例如,您可以查看 NoException 库:https ://noexception.machinezoo.com/
它为您提供了一种方便的方法来包装/潜行/记录/忽略已检查或未检查的异常。
例如,在您的情况下,它将是:
.map(value -> Exceptions.sneak().function(mapper::doMap))
或者
.map(value -> Exceptions.wrap().function(mapper::doMap))
PS:我不是图书馆的作者,也不是贡献者,但我在几个项目中使用过这个图书馆。
推荐阅读
- bash - 为什么我的 find 和 xargs 复制命令适用于一个文件夹而不适用于另一个文件夹?
- assembly - x86 条件跳转:与立即零或零寄存器比较更快?
- schema.org - 如何在 schema.org Json-LD 中指定多个选项(汽车)?
- python - 将矩阵拆分为多个矩阵
- html - 当图像在容器内缩小时,填充底部黑客不起作用
- sql - 嵌套查询中的 SQL where 子句与嵌套查询中不存在的列
- angular - Angular 8 Observable.interval 改变了吗?
- hla - OpenRTI 回调的问题
- chisel - 在 Chisel 中循环循环缓冲区
- node.js - 使用 Content-Transfer-Encoding 的消息编码错误:二进制