gpt4 book ai didi

java - 是否使用 try-with-resources 语句声明 Stream 有什么区别?

转载 作者:塔克拉玛干 更新时间:2023-11-01 21:32:22 26 4
gpt4 key购买 nike

在 Java 8 中,Stream(它是 AutoCloseable)不能被重用,一旦被消费或使用,流将被关闭。那么用 try-with-resources 语句声明的实用程序是什么?

带有 try-with-resources 语句的示例:

    public static void main(String[] args) throws IOException {

try (Stream<Path> entries
= Files.walk(Paths.get("."), 4, FileVisitOption.FOLLOW_LINKS)) {
entries.forEach(x -> System.out.println(x.toAbsolutePath()));// the entries stream will be automatically closed at this point
//..
System.out.println("Still in the Try Block");
} //The entries will be closed again because it is declared in the try-with-resources statement
}

这里是没有 try catch block 的相同示例

public static void main(String[] args) throws IOException {
Stream<Path> entries = Files.walk(Paths.get("."), 4, FileVisitOption.FOLLOW_LINKS);
entries.forEach(x -> System.out.println(x.toAbsolutePath()));// the entries stream will be automatically closed at this point
System.out.println("Is there a risk of resources leak ?");
}

哪个更安全?

经过一些回答后,我更新了我的代码以检查流是否已关闭:

这里是新代码:

public static void main(String[] args) throws IOException {

resourceWithTry();
resourceWithoutTry();
}

private static void resourceWithTry() throws IOException {
try (Stream<Path> entries
= Files.walk(Paths.get("."), 4, FileVisitOption.FOLLOW_LINKS).onClose(() -> System.out.println("The Stream is closed"))) {
entries.forEach(x -> System.out.println(x.toAbsolutePath()));// the entries stream will be not automatically closed at this point
System.out.println("Still in the Try Block");
} //The entries will be closed again because it is declared in the try-with-resources statement
}

private static void resourceWithoutTry() throws IOException {
Stream<Path> entries
= Files.walk(Paths.get("."), 4, FileVisitOption.FOLLOW_LINKS).onClose(() -> System.out.println("Without Try: The Stream is closed"));
entries.forEach(x -> System.out.println(x.toAbsolutePath()));// the entries stream will be not automatically closed at this point
System.out.println("Still in the Try Block");
}

最佳答案

In Java 8, Stream (which is AutoCloseable) cannot be reused, once it is consumed or used, the stream will be closed.

不完全是。
Stream forEach()等终端操作不要关闭流。
它使流管道不再是可消耗的。
这是不同的。

Package java.util.stream description状态:

After the terminal operation is performed, the stream pipeline is considered consumed, and can no longer be used; if you need to traverse the same data source again, you must return to the data source to get a new stream.

它并没有说流已关闭。

所以在下面的代码中,AutoCloseable.close() Stream 的方法永远不会调用实例:

Stream<Path> entries = Files.walk(Paths.get("."), 4, FileVisitOption.FOLLOW_LINKS);
entries.forEach(x -> System.out.println(x.toAbsolutePath()));

那么是否总是需要关闭流? (使用显式 close() 调用或更好的 try-with-resources )

java.util.stream.Stream<T> javadocs 解释说几乎所有 Stream实例不需要用 AutoCloseable.close() 关闭使用后。
仅对 IO 流有效。

Streams have a close() method and implement AutoCloseable, but nearly all stream instances do not actually need to be closed after use. Generally, only streams whose source is an IO channel (such as those returned by Files.lines(Path, Charset)) will require closing. Most streams are backed by collections, arrays, or generating functions, which require no special resource management. (If a stream does require closing, it can be declared as a resource in a try-with-resources statement.)

在我们的例子中,您操纵 File s,所以关闭 channel 是有意义的。
通过使用 try-with-resources ,您可以避免可能发生的资源耗尽异常和错误。
如果在处理过程中出现任何错误或异常,资源可能会被释放。

关于java - 是否使用 try-with-resources 语句声明 Stream 有什么区别?,我们在Stack Overflow上找到一个类似的问题: https://stackoverflow.com/questions/47108164/

26 4 0
Copyright 2021 - 2024 cfsdn All Rights Reserved 蜀ICP备2022000587号
广告合作:1813099741@qq.com 6ren.com