java - 使用 Java 可选 ifPresentOrElse 方法时无法抛出“已检查”异常
问题描述
ifPresentOrElse
为什么在使用java Optional 方法时不能在 orElse 部分中抛出已检查的异常?
例如:
dao.findBook(id).ifPresentOrElse(book -> {
printingService.print(book, printerName);
changeBookPrintDate(book.getId(), LocalDateTime.now());
}, () -> new BookNotFoundException());
哪里BookNotFoundException
是自定义异常扩展Exception
类(检查异常)。
但是这段代码让编译器不高兴:
unreported exception com...exception.BookNotFoundException; must be caught or declared to be thrown
(知道它已经在方法声明中抛出,并且用 try catch 包围这个块并不能解决编译问题)。
但是,如果我们进行BookNotFoundException
扩展RuntimeException
(未选中),那么一切都可以完美运行。
任何人都知道为什么?
阻止在这个 java 9 Optional 方法中抛出这种异常的原因是什么?
为什么我应该将我的异常设置为 RuntimeException 以使其工作,而它更多地被视为“自定义异常”而不是“运行时”?
这个问题解决了同样的问题,但对于 java 8 lambdas,所以我不知道这是否同样适用于 java 9 Optionals。
任何想法 ?
解决方案
ifPresentOrElse
当您想要指定两个非抛出操作时,该方法是一个有用的工具,以便在任何一种情况下都可以在方法调用之后继续。但是当你想在没有值的情况下抛出时,这是一个不必要的复杂化。只需使用
var book = dao.findBook(id).orElseThrow(BookNotFoundException::new);
printingService.print(book, printerName);
changeBookPrintDate(book.getId(), LocalDateTime.now());
由于此构造将抛出不存在的值,因此代码流将仅针对当前值继续。所以你可以book
像普通的局部变量一样在后续代码中使用,但要保证它永远不会是null
.
该方法orElseThrow
期望Supplier
抛出异常,而不是抛出的函数。这样,供应商可以构造一个检查异常而不抛出它,并且orElseThrow
声明的通用签名可以抛出供应商产生的任何类型。
public <X extends Throwable> T orElseThrow(Supplier<? extends X> exceptionSupplier) throws X
推荐阅读
- javascript - cocos creator 的自定义 html 按钮
- json - 使用另一个多行文件的输出编辑 json 文件
- php - 使用 PHP $_SESSION 变量,然后取消设置
- keras - Keras 中 CuDNNLSTM 的辍学
- arrays - 将事件索引与时间向量合并 Matlab
- docker - 无法完成与 Docker Container 内的套接字服务器的连接,而未容器化的同一个 gunicorn 服务器工作正常
- java - Webstart 上的 Netbeans“无法启动应用程序”
- pandas - PatsyError:数据参数和列之间的行数不匹配(statsmodels)
- python - 通过自己的数据集进行 YOLO 训练
- r - 向量列表中的grepl和子集?