我是Java8的新手,我的一个问题是如何使用Stream将Map<K, List<V>>转换为Map<V, List<K>>。例如:
input: {A => [B, C, D], E => [F]}
output: {B => A, C => A, D => A, F => E}
假设列表中没有重复的值。如何在Java 8流中以优雅的方式实现?
祝好,
Wei
我是Java8的新手,我的一个问题是如何使用Stream将Map<K, List<V>>转换为Map<V, List<K>>。例如:
input: {A => [B, C, D], E => [F]}
output: {B => A, C => A, D => A, F => E}
如果你想不使用forEach()
来解决问题,你可以这样做:
Map<Integer, String> pam =
map.entrySet().stream()
.flatMap(x -> x.getValue().stream().map(v -> new AbstractMap.SimpleEntry<>(v, x.getKey())))
.collect(Collectors.toMap(Map.Entry::getKey, Map.Entry::getValue));
对于每个入口,如"3"-> [3,4,5,6]
,将创建一组条目流,如3->3,4->3,5->3,6->3
,使用flatMap
可将其展平为一个流,然后Collectors.toMap()
创建最终的Map
。
Map<String, List<Integer>> map = new HashMap<>();
Map<Integer,String> pam = new HashMap<>();
map.entrySet().stream().forEach(e -> e.getValue().stream().forEach(v -> pam.put(v, e.getKey())));
Set<E>
实现自 Collection
的 stream()
接口。其余部分只是将东西插入到正确的位置。另外,正如 @user140547 (谢谢)建议的那样,还有一个更简单的解决方案。 map.forEach((k,v) -> v.forEach(vv -> pam.put(vv, k)));
使用由我编写的免费StreamEx库非常简单:
EntryStream.of(map).invert().flatMapKeys(Collection::stream).toMap();
这里的EntryStream.of(map)
创建了一个map条目流,可以通过其他操作进行扩展;invert()
交换键和值,flatMapKeys()
将键扁平化,保持值不变,toMap()
将结果条目收集回map。
正如@JimGarrison所指出的那样,使用Map.forEach会更容易
input.forEach( (key,value)-> value.forEach(vvalue -> output.put(vvalue, key)));