从地图列表创建地图 [英] Create a map from a list of maps

查看:20
本文介绍了从地图列表创建地图的处理方法,对大家解决问题具有一定的参考价值,需要的朋友们下面随着小编来一起学习吧!

问题描述

我有一张地图列表.

List<Map<Integer, String>>

列表中的值是,例如

<1, String1>
<2, String2>
<1, String3>
<2, String4>

作为最终结果,我想要一张地图>,比如

As an end result, I want a Map>, like

<1, <String1, String3>>
<2, <String2, String4>>

如何在 Java 中实现这一点.

How can I achieve this in Java.

代码:

List<Map<Integer, String>> genericList = new ArrayList<Map<Integer,String>>();
for(TrackActivity activity : activityMajor){
Map<Integer, String> mapIdResponse = activity.getMapIdResponse();
genericList.add(mapIdResponse);
}

现在这个 genericList 是输入,来自这个列表,基于我想要的相同 id

Now this genericList is the input and from this list, based on the same ids I want a

Map<Integer, List<String>> mapIdResponseList

基本上,将基于 id 的 String 响应组合在一起,将具有相同 id 的响应分组到一个列表中,然后创建一个以该 id 作为键和列表作为其值的新映射.

Basically, to club the responses which are String based on the ids, grouping the responses with same id in a list and then creating a new map with that id as the key and the list as its value.

推荐答案

您可以使用 Java 8 执行以下操作:

You can do it the following with Java 8:

private void init() {
    List<Map<Integer, String>> mapList = new ArrayList<>();

    Map<Integer, String> map1 = new HashMap<>();
    map1.put(1, "String1");
    mapList.add(map1);

    Map<Integer, String> map2 = new HashMap<>();
    map2.put(2, "String2");
    mapList.add(map2);

    Map<Integer, String> map3 = new HashMap<>();
    map3.put(1, "String3");
    mapList.add(map3);

    Map<Integer, String> map4 = new HashMap<>();
    map4.put(2, "String4");
    mapList.add(map4);

    Map<Integer, List<String>> response = mapList.stream()
            .flatMap(map -> map.entrySet().stream())
            .collect(
                    Collectors.groupingBy(
                            Map.Entry::getKey, 
                            Collectors.mapping(
                                    Map.Entry::getValue, 
                                    Collectors.toList()
                            )
                    )
            );
    response.forEach((i, l) -> {
        System.out.println("Integer: " + i + " / List: " + l);
    });
}

这将打印:

整数:1/列表:[String1, String3]
整数:2/列表:[String2, String4]

Integer: 1 / List: [String1, String3]
Integer: 2 / List: [String2, String4]

解释(非常有根据),恐怕我无法解释每一个细节,您需要先了解Java 8中引入的StreamCollectors API的基础知识:

Explanation (heavily warranted), I am afraid I cannot explain every single detail, you need to understand the basics of the Stream and Collectors API introduced in Java 8 first:

  1. mapList中获取一个Stream>.
  2. 应用 flatMap 运算符,它将流大致映射到现有流.
    这里:我将所有 Map 转换为 Stream> 并将它们添加到现有流中,因此现在是也是 Stream> 类型的.
  3. 我打算将 Stream<Map.Entry<Integer, String>> 收集到一个 Map 中.
  4. 为此,我将使用 Collectors.groupingBy,它基于分组函数生成 Map>在这种情况下,将 Map.Entry 映射到 Integer 的函数.
  5. 为此,我使用了一个方法引用,它完全符合我的要求,即 Map.Entry::getKey,它对 Map.Entry 进行操作并返回一个整数.
  6. 如果我没有做任何额外的处理,此时我将有一个 Map.
  7. 为了确保我得到正确的签名,我必须向 Collectors.groupingBy 添加一个下游,它必须提供一个收集器.
  8. 对于这个下游,我使用了一个收集器,它通过参考 Map.Entry::getValueMap.Entry 条目映射到它们的 String 值>.
  9. 我还需要指定它们是如何被收集的,这里只是一个 Collectors.toList(),因为我想将它们添加到一个列表中.
  10. 这就是我们获得Map<Integer, List,String>>的方式.
  1. Obtain a Stream<Map<Integer, String>> from the mapList.
  2. Apply the flatMap operator, which roughly maps a stream into an already existing stream.
    Here: I convert all Map<Integer, String> to Stream<Map.Entry<Integer, String>> and add them to the existing stream, thus now it is also of type Stream<Map.Entry<Integer, String>>.
  3. I intend to collect the Stream<Map.Entry<Integer, String>> into a Map<Integer, List<String>>.
  4. For this I will use a Collectors.groupingBy, which produces a Map<K, List<V>> based on a grouping function, a Function that maps the Map.Entry<Integer, String> to an Integer in this case.
  5. For this I use a method reference, which exactly does what I want, namely Map.Entry::getKey, it operates on a Map.Entry and returns an Integer.
  6. At this point I would have had a Map<Integer, List<Map.Entry<Integer, String>>> if I had not done any extra processing.
  7. To ensure that I get the correct signature, I must add a downstream to the Collectors.groupingBy, which has to provide a collector.
  8. For this downstream I use a collector that maps my Map.Entry entries to their String values via the reference Map.Entry::getValue.
  9. I also need to specify how they are being collected, which is just a Collectors.toList() here, as I want to add them to a list.
  10. And this is how we get a Map<Integer, List,String>>.

这篇关于从地图列表创建地图的文章就介绍到这了,希望我们推荐的答案对大家有所帮助,也希望大家多多支持IT屋!

查看全文
登录 关闭
扫码关注1秒登录
发送“验证码”获取 | 15天全站免登陆