【问题标题】:Java 8 Stream function grouping to Map where value is a MapJava 8 Stream 函数分组到 Map ,其中 value 是 Map
【发布时间】:2020-01-30 13:46:04
【问题描述】:

我正在尝试收集列表的结果并将它们组织到一个地图中,其中值是一个地图:

private Map<Organisation, Map<LocalDate, Status>> getSummaries(final List<Status> summaries) {
    return summaries
            .stream()
            .collect(groupingBy(Status::getOrganisation,
                    toMap(Status::getProcessedDate, Function.identity())));
}

我收到java.lang.IllegalStateException: Duplicate key 错误,因为getProcessedDate() 对于列表中的不同值是相同的。

有没有办法可以将具有相同processeddate 的多个对象合并到地图中?

例如说我在列表中有这些对象:

Summary(ProcesseDate=2020-01-30, Organisation=ABC, status=OK, statusCount=5)
Summary(ProcesseDate=2020-01-30, Organisation=ABC, status=FAILED, statusCount=2)
Summary(ProcesseDate=2020-01-30, Organisation=APPLE, status=OK, statusCount=5)
Summary(ProcesseDate=2020-01-30, Organisation=APPLE, status=REJECTED, statusCount=5)

地图中包含的值应该是:

key=ABC
   value { key=2020-01-30, value= Summary(ProcesseDate=2020-01-30, Organisation=ABC, status=OK, statusCount=5), Summary(ProcesseDate=2020-01-30, Organisation=ABC, status=FAILED, statusCount=2) }

当我尝试toMap(Status::getProcessedDate, Function.identity(), (v1, v2) -&gt; v2))); 时,它会删除其中一个条目

【问题讨论】:

  • 将map的value类型改为list,在这个阶段合并(v1,v2) -> v1.add(v2);返回 v1;

标签: java java-8 java-stream collectors


【解决方案1】:

如果您不想合并数据并且没有唯一键,您可能只是在寻找嵌套分组:

private Map<Organisation, Map<LocalDate, List<Status>>> getSummaries(final List<Status> summaries) {
    return summaries
            .stream()
            .collect(groupingBy(Status::getOrganisation, groupingBy(Status::getProcessedDate)));
}

【讨论】:

    【解决方案2】:

    如果要合并key,可以使用Map.merge()

    map.merge(key, value, bifunction); 检查地图中是否存在key。如果不是,则调用map.put(key, value);。如果是,则将bifunction 应用于现有的键和值,并将其存储在映射中。

    例如,如果您有一个 Map&lt;String, Integer&gt; 来计算段落中某个单词的出现次数,您可以使用以下代码:

    List<String> words = ...
    Map<String, Integer> wordCount = ...
    
    words.forEach(s -> wordCount.merge(s, 1, (word, count) -> count + 1));
    

    您可以使用它来避免在代码中添加重复键。

    【讨论】:

      猜你喜欢
      • 2020-10-04
      • 2018-02-18
      • 2021-08-19
      • 1970-01-01
      • 2017-02-12
      • 1970-01-01
      • 1970-01-01
      • 2020-04-08
      • 1970-01-01
      相关资源
      最近更新 更多