我想使用此代码只读取文件中的第一行:
String line = Files.lines(path).findFirst().get();
我认为这不会将整个文件的内容加载到内存中。相反,它打开文件,只读取第一行,然后关闭文件。
我的假设是否正确?
答案 0 :(得分:6)
静态流线(路径路径) - 从文件中读取所有行作为 流。
Files.lines(path)
读取所有行,这意味着它们有可能被访问,但加载到内存中的内容取决于流所需的内容。在您的情况下,只会访问第一行(存储在内存中),因为BufferedReader
可以根据需要懒惰地将内容加载到内存中。
答案 1 :(得分:5)
Files#lines
方法使用BufferedReader
类来使用BufferedReader#lines
访问这些行。来自source
返回一个Stream,其元素是从中读取的行 BufferedReader中。 java.util.stream.Stream是懒惰填充的,即, 只读在终端流操作期间发生。读者必须 在终端流的执行期间不操作 操作。否则,终端流操作的结果是 未定义。
执行终端流操作后没有 保证读者将处于特定的位置 阅读下一个字符或行。
如果在访问底层证书时抛出IOException BufferedReader,它包含在一个UncheckedIOException中 从Stream方法抛出,导致读取发生。这个 如果在BufferedReader上调用,则该方法将返回Stream 关闭。该流上的任何操作都需要从中读取 BufferedReader在关闭后会导致UncheckedIOException 被抛出。
public Stream<String> lines() {
Iterator<String> iter = new Iterator<String>() {
String nextLine = null;
@Override
public boolean hasNext() {
if (nextLine != null) {
return true;
} else {
try {
nextLine = readLine();
return (nextLine != null);
} catch (IOException e) {
throw new UncheckedIOException(e);
}
}
}
@Override
public String next() {
if (nextLine != null || hasNext()) {
String line = nextLine;
nextLine = null;
return line;
} else {
throw new NoSuchElementException();
}
}
};
return StreamSupport.stream(Spliterators.spliteratorUnknownSize(
iter, Spliterator.ORDERED | Spliterator.NONNULL), false);
}
Stream
创建的StreamSupport.stream
由Iterator
支持。只询问一个元素,因为您调用了Stream#findFirst
。因此,只需拨打hasNext
和next
一次,这意味着BufferedReader#readLine
只会被调用一次。