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

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

问题描述

 列表< Map< Integer,String>> 

列表中的值是,例如

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

作为最终结果,我想要一个Map>,就像

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

如何在Java中实现此功能。



CODE:

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





$ b现在这个泛型列表是输入,并从这个列表中,基于相同的ID我想要一个

  Map< Integer,List< String>> mapIdResponseList 

基本上,为了将基于id的String响应分组,使用相同的id在列表中,然后创建一个新的地图,该地图的ID为该键,列表为值。

解决方案

对于Java 8来说它如下:

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

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

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

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

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

Map< Integer,List< String>>响应= 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]




解释(严重担保),恐怕我无法解释每一个细节,您需要了解 Stream 的基本知识。和 Collectors 首先在Java 8中引入的API:


  1. 获取<$ c $从 mapList
  2. 中输入流<映射<整数,字符串>>

  3. code> flatMap 运算符,它将一个流粗略地映射到一个已经存在的流中。 到 Stream< Map.Entry< Integer,String>>> 并将它们添加到现有流中,因此现在它也是类型 Stream< Map.Entry< Integer,String>>

  4. 我打算收集 Stream< Map。条目< Integer,Str < / code>>< code>映射<整数,列表< String>> 。我将使用一个 Collectors.groupingBy ,它会根据a Map< / code>生成一个 Map.Entry< Integer,String> 映射到一个函数 Function 整数在这种情况下。

  5. 为此,我使用方法引用,它正是我想要的,即 Map.Entry :: getKey ,它在 Map.Entry 上运行,并返回一个整数

  6. 在这一点上,如果我有一个 Map< Integer,List< Map.Entry< Integer,String>>> 没有做任何额外的处理。

  7. 为了确保我得到正确的签名,我必须向 Collectors.groupingBy 添加一个下游,它必须提供一个收集器。
  8. 对于这个下游,我使用一个收集器将我的 Map.Entry 条目映射到它们的 S饰ng 值通过引用 Map.Entry :: getValue

  9. 我还需要指定它们如何正在收集,这是一个 Collectors.toList()这里,因为我想将它们添加到列表中。

  10. 并且这是我们如何得到 Map<整数,列表,字符串>>


I have a list of maps.

List<Map<Integer, String>>

The values in the list are, for example

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

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

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

How can I achieve this in Java.

CODE :

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

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

Map<Integer, List<String>> mapIdResponseList

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.

解决方案

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);
    });
}

This will print:

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

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. 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天全站免登陆