0
 Map<String, List<String>> map1 = new HashMap<>();
  Map<String, List<String>> map2 = new HashMap<>();
   map1.put("a", Lists.newArrayList("1","123"));
    map1.put("b", Lists.newArrayList("2","223"));

    map2.put("c", Lists.newArrayList("11","1123"));
    map2.put("a", Lists.newArrayList("22","2223"));
  Map<String, List<List<String>>> collect = Stream.of(map1, map2)
            .flatMap(m -> m.entrySet().stream())
            .collect(Collectors.groupingBy(Map.Entry::getKey,
                    Collectors.mapping(Map.Entry::getValue,
                            Collectors.toList())
            ));
 System.out.println(collect);

print: {a=[[1, 123], [22, 2223, 1, 123]], b=[[2, 223]], c=[[11, 1123]]}

how can print: {a=[22, 2223, 1, 123], b=[2, 223], c=[11, 1123]}

jane
  • 61
  • 5

2 Answers2

0

You may use a simple for loop and do it like this.

List<Map<String, List<String>>> source = Arrays.asList(map1, map2);
for (Map<String, List<String>> m : source) {
    for (Map.Entry<String, List<String>> e : m.entrySet()) {
        target.computeIfAbsent(e.getKey(), unused -> new ArrayList<>())
            .addAll(e.getValue());
    }
}

A stream based counterpart would be something like this.

Map<String, List<String>> res = source.stream()
    .flatMap(m -> m.entrySet().stream())
    .collect(Collectors.groupingBy(Map.Entry::getKey,
        Collectors.flatMapping(e -> e.getValue().stream(), Collectors.toList())));

The Collectors.flatMapping is available from java9 onwards. If you are using java8, I would recommend you to write your own custom collector for flatMapping and use it here. This will give you an easier migration strategy for Java9 too. You may find an explanation here.

Ravindra Ranwala
  • 20,744
  • 6
  • 45
  • 63
  • Thank you for your answer, but the API( Collectors.flatMapping) is java9, and I use java8。Finally, I try another way: map1.forEach((k, v) -> map2.merge(k, v, (v1, v2) -> { v1.addAll(v2); return v1; })); – jane Feb 10 '22 at 02:56
  • Please see my edit and go through this answer: https://stackoverflow.com/questions/39130122/java-8-nested-multi-level-group-by/39131049#39131049 – Ravindra Ranwala Feb 10 '22 at 03:17
  • Good solution, thank you @Ravindra Ranwala – jane Feb 10 '22 at 03:25
0

I wouldn't create List<List<String>>s in the first place

Map<String, List<String>> map1 = new HashMap<>();
Map<String, List<String>> map2 = new HashMap<>();
map1.put("a", Lists.newArrayList("1","123"));
map1.put("b", Lists.newArrayList("2","223"));

map2.put("c", Lists.newArrayList("11","1123"));
map2.put("a", Lists.newArrayList("22","2223"));

Map<String, List<String>> collect = Stream.of(map1, map2)
        .flatMap(m -> m.entrySet().stream())
        .collect(Collectors.groupingBy(Map.Entry::getKey,
                 Collectors.flatMapping(e -> e.getValue().stream(), Collectors.toList())));
Caleth
  • 52,200
  • 2
  • 44
  • 75