【发布时间】:2017-09-16 04:13:26
【问题描述】:
假设我有一个 Java8 Stream<FileReader> 并且我使用该流到 map 等,我如何控制流中使用的 FileReaders 的关闭?
请注意,我可能无法访问个人FileReaders,例如:
filenames.map(File::new)
.filter(File::exists)
.map(f->{
BufferedReader br = null;
try {
br = new BufferedReader(new FileReader(f));
} catch(Exception e) {}
return Optional.ofNullable(br);
})
.filter(Optional::isPresent)
.map(Optional::get)
.flatMap(...something that reads the file contents...) // From here, the Stream doesn't content something that gives access to the FileReaders
在做了一些其他的映射等之后,我终于在续集中失去了FileReaders。
我最初认为垃圾收集器能够在需要时执行此操作,但是当 filenames 是长 Stream 时,我经历了操作系统描述符耗尽。
【问题讨论】:
-
这种映射读者自己的设计会导致问题。更好地处理在一个 lambda 中读取所有文件。首先避免使用
Stream<FileReader>。 -
@LouisWasserman 你的意思是比这个问题更多?哪个?
-
嗯,使用一个 try-with-resources 语句来控制读者的整个生命周期等通常是一种很好的做法。
-
我的意思是您不打算以这种方式设计您的流。 (更不用说尝试在中间进行 I/O 操作的复杂性了......)您可能可以通过在您的 flatMap 中执行关闭操作来将其破解,但它仍然是会比尝试使用单个 try-with-resources lambda 更尴尬。
-
这是一个典型的案例,我更喜欢旧的命令式方法,而不是使用流来打自己的脚。或者,如果您坚持使用流,我会将所有文件处理移至私有方法。
标签: java file java-8 java-stream