我有两个地图 m1
和 m2
类型为 Map
基于我探索的解决方案:
Map<Integer, List<String>> collated =
Stream.concat(m1.entrySet().stream(), m2.entrySet().stream()).collect(
Collectors.toMap(Entry::getKey,
Entry::getValue, (a, b) -> {
List<String> merged = new ArrayList<String>(a);
merged.addAll(b);
return merged;
}));
但是,此解决方案期望源
列表
为映射
我不想改变源集合。请提供使用lambda表达式实现这一点的输入。
如果你想要纯Java-8的解决方案,米沙的解决方案是最好的。如果不介意用第三方库的话,用我的StreamEx会短一点。
Map<Integer, List<String>> map = StreamEx.of(m1, m2)
.flatMapToEntry(Function.identity())
.grouping();
从内部来说,它和米沙的解决方案是一样的,只是语法糖。
匿名用户
我现在不能测试它,但是我认为您需要它来将值的映射从< code>Entry::getValue更改为包含该值的列表:
Map<Integer, List<String>> collated =
Stream.concat(m1.entrySet().stream(), m2.entrySet().stream())
.collect(Collectors.toMap(Entry::getKey,
e -> {
List<String> v = new ArrayList<String>();
v.add(e.getValue());
return v;
},
(a, b) -> {
List<String> merged = new ArrayList<String>(a);
merged.addAll(b);
return merged;
}));
编辑:这个想法是正确的。语法不是。当前的语法有效,尽管有点难看。一定有更短的方法来编写它。
您也可以替换e-
或使用e-
或者您可以使用< code >分组方式
来完成:
Map<Integer, List<String>> collated =
Stream.concat(m1.entrySet().stream(), m2.entrySet().stream())
.collect(Collectors.groupingBy(Map.Entry::getKey,
Collectors.mapping(Map.Entry::getValue,
Collectors.toList())));
这是groupingBy
收集器的工作:
Stream.of(m1,m2)
.flatMap(m->m.entrySet().stream())
.collect(groupingBy(
Map.Entry::getKey,
mapping(Map.Entry::getValue, toList())
));
我试图使用
我想按id分组。 结果应如下所示: 静态编程语言中最惯用的方法是什么?
问题内容: 我有两张这样的地图: 我想做的就是将两个地图合并成 这样: 如果不在中,则将条目添加到中。 如果不在,则相同,将条目添加到中。 如果在中,则添加此条目: 我已经阅读了有关,但是我确实很难使用它。任何线索如何做到这一点? 谢谢!! 问题答案: 我认为这是可行的 合并功能将解决方案3,因为如果密钥已经存在,它将使用v1.mark1和v2.mark2创建一个新的MyObject。
问题内容: 我想将两个Map与JAVA 8 Stream合并: 我尝试使用此实现: 但是,此实现只会产生如下结果: 如果中没有包含一个键,则会将其作为新键添加到相应的String列表中。如果键在和中重复,则两个值列表将被合并为:,然后是。 问题答案: 您可以通过遍历中的所有条目并将它们合并到中来实现此目的。 下面通过调用操作消耗每个条目的键和值的位置来遍历的条目。对于每个条目,我们叫上:这将要么创
问题内容: 我有两个键为s且值为的映射。给定两个s,合并它们的最简单方法是什么,如果两个键相同,则值是两个集合的并集。您可以假设值永远不会为null,并且如果有用的话,我们可以将它们设为s。 问题答案: 我们在谈论实例。在这种情况下,查找值为O(1),因此您只需获取一个映射,然后对该映射的条目进行迭代,看看另一个映射是否包含该键。如果没有,只需添加设置。如果包含密钥,则将两个集合并集(通过将一个集