Java8:如何从流中聚合对象?

塞伯

编辑

恕我直言:我认为这不是重复的,因为这两个问题试图以不同的方式解决问题,尤其是因为它们提供的技术技能完全不同(最后,因为我问自己这两个问题)。

问题

如何从有序流中聚合项目,最好在中间操作中进行聚合?

语境

我的另一个问题:Java8流线并在终端线上进行动作聚合

我有一个非常大的格式文件:

MASTER_REF1
    SUBREF1
    SUBREF2
    SUBREF3
MASTER_REF2
MASTER_REF3
    SUBREF1
    ...

SUBREF(如果有)适用于MASTER_REF,并且两者都是复杂的对象(您可以想象它有点JSON)。

null乍一看,我试图对行进行分组,并在汇总时返回操作,并在找到一组行时返回一个值(如果,则“行”结束line.charAt(0)!=' ')。

此代码难以阅读,需要输入.filter(Objects::nonNull)

我认为可以使用a.collect(groupingBy(...))或a来实现这一点,.reduce(...)但这些是终端操作,即:

  • 在我的情况下不是必需的:线是有序的,应该按它们的位置分组,然后再变换线组(map + filter + ... + foreach);
  • 也不是一个好主意:我说的是一个巨大的数据文件,它比RAM + SWAP的总量大得多……终端操作会使可用资源饱和(如前所述,我需要将组保留在内存中,因为将在之后进行转换)
塔吉尔·瓦列夫(Tagir Valeev)

正如我在上一个问题答案中已经指出的那样,可以使用一些提供部分归约操作的第三方库。我自己开发的StreamEx就是此类库之一

在StreamEx库中,部分归约操作是中间流操作,它在满足某些条件的同时合并了多个输入元素。通常,条件是通过BiPredicate应用到一对相邻的流元素来指定的true当元素应该组合在一起时,返回该对元素组合元素的最简单方法是制作如下所示的ListviaStreamEx.groupRuns()方法:

Stream<List<String>> records = StreamEx.of(Files.lines(path))
    .groupRuns((line1, line2) -> !line2.startsWith("MASTER"));

在这里,当两条相邻行中的第二行以"MASTER"(如您的示例)开头时,我们将开始一个新记录否则,我们继续上一个记录。

请注意,这样的流仍然是惰性的。在顺序处理中,一次最多List<String>创建一个中间体还支持并行处理,尽管将Files.lines流转换为并行模式很少会提高性能(至少在Java-9之前)。

本文收集自互联网,转载请注明来源。

如有侵权,请联系 [email protected] 删除。

编辑于
0

我来说两句

0 条评论
登录 后参与评论

相关文章

如何计算Java8流中按属性分组的对象分组中的多个和?

如何使用Java8流和groupBy从地图获取多级聚合结果?

如何确保java8流中的处理顺序?

如何在Java8流中管理附带影响

列表流JAVA8中的列表

java8聚合对象转换器

如何从列表<object>由对象采取多个域值与Java8流创建HashSet的?

Java8流使用流畅的API减少对象列表

您如何总结Java 8流中的对象列表

如何将Java8流的元素添加到现有列表中

使用Java8运行时如何在流中获取新的用户输入

使用Java8流减少Java列表中的元素

Java8减少流

我们可以通过Java8中的流将值赋给对象中的变量吗?

Java 8流聚合地图

我如何排序与java8流TreeSets的列表

Java8流文件,如何控制文件的关闭?

如何使用Java8 Lambda反向排序流?

试图了解Java8中流的distinct()

在Java8流中处理null的BigDecimals

是否可以在Java8流中重写此类代码?

如何在Java8中将对象数组转换为用户定义的对象

聚合Java 8流中的运行时异常

惯用枚举Java 8中的对象流

如何使用流从Java 8中的对象列表中根据对象的某些属性找到总和

如何拆分的ArrayList在一行中的多个列出了特定属性对象Java8

如何在Java8 Lambda表达式中求和对象的BigDecimal属性?

如何在Java8中使用流返回特定类型的数组而不是泛型类型的数组

如何检测信息流并跟踪进度?(香草Java8或cylcops反应型反应流)