Java 8 流与集合存储

2022-09-03 03:36:34

我一直在阅读Java 8 Streams以及从数据源流式传输数据的方式,而不是从中提取数据的整个集合。

这句话特别让我在一篇关于Java 8中流的文章中读到过。

无存储。流没有值的存储;它们通过计算步骤管道从源(可以是数据结构,生成函数,I / O通道等)携带值。

我理解了逐个从源中流式传输数据的概念。我不明白的是,如果您从集合流式传输,为什么没有存储?集合已存在于堆上,您只是从该集合流式传输数据,集合已存在于“存储”中。

如果我只使用标准的 for 循环遍历集合,那么内存占用量有什么区别?


答案 1

关于流和存储的声明意味着流没有任何自己的存储。如果流的源是一个集合,那么显然该集合具有保存元素的存储。

让我们从那篇文章中举一个例子:

int sum = shapes.stream()
                .filter(s -> s.getColor() == BLUE)
                .mapToInt(s -> s.getWeight())
                .sum();

假设这是一个具有数百万个元素的。人们可能会想象,该操作将循环访问源中的元素并创建一个临时的结果集合,该集合也可能具有数百万个元素。然后,该操作可能会循环访问该临时集合并生成要求和的结果。shapesCollectionfiltermapToInt

这不是它的工作方式。没有临时的中间集合。流操作是流式的,因此从中出现的元素被传递并传递到集合中,而不会被存储到集合中并从中读取。filtermapToIntsum

如果流源不是集合(例如,从网络集合中读取元素),则根本不需要任何存储。如下所示的管道:

int sum = streamShapesFromNetwork()
                .filter(s -> s.getColor() == BLUE)
                .mapToInt(s -> s.getWeight())
                .sum();

可能会处理数百万个元素,但它不需要在任何地方存储数百万个元素。


答案 2

将流想象成连接到水箱的喷嘴,水箱是您的数据结构。喷嘴没有自己的存储。当然,流提供的水(数据)来自具有存储的来源,但流本身没有存储。将另一个喷嘴(流)连接到您的水箱(数据结构)不需要存储数据的全新副本。