我正在升级一些现有的API,这些API将Iterable
设为AutoCloseable
- 敏感。例如,给定:
/**
* @throws NoSuchElementException
*/
public static <T> T getOne(Iterable<T> iterable) {
return iterable.iterator().next();
}
我希望该方法关闭迭代器,如果它是可关闭的。这是我到目前为止所得到的:
/**
* @throws NoSuchElementException
*/
public static <T> T getOne(Iterable<T> iterable) {
Iterator<T> iterator = iterable.iterator();
try {
return iterable.iterator().next();
} finally {
if (iterator instanceof AutoCloseable) {
try {
((AutoCloseable) iterator).close();
} catch (Exception ignored) {
// intentionally suppressed
}
}
}
}
鉴于JDK文档如何引用Throwable.getSuppressed()
,该代码是否应该采取类似于以下内容的方式?
} catch (Exception x) {
RuntimeException rte = new RuntimeException("Could not close iterator");
rte.addSuppressed(x);
throw rte;
}
答案 0 :(得分:3)
我认为,如果您发现自己有try-with-resources
,那么最好的办法就是捎带AutoCloseable
构造,如下所示:
/**
* @throws NoSuchElementException
*/
public static <T> T getOne(Iterable<T> iterable) {
Iterator<T> iterator = iterable.iterator();
if (iterator instanceof AutoCloseable) {
try (AutoCloseable c = (AutoCloseable) iterator) {
return iterator.next();
}
} else {
return iterator.next();
}
}
然后语言级构造将以正确的方式处理异常(包括在close
方法中)。