繁体   English   中英

Java Streams将EnumMap的Map转换为列表的Map

[英]Java Streams transform Map of EnumMap into a Map of lists

我想转换以下内容

enum Parameter {Foo, Bar, Baz};

Map<String, EnumMap<Parameter, String>> myMap = new HashMap(){{
   put("KEY1", new EnumMap<>(Parameter.class) {{
      put(Parameter.Foo, "BAD");
      put(Parameter.Bar, "GOOD");
      put(Parameter.Baz, "BAD");
   }});
   put("KEY2", new EnumMap<>(Parameter.class) {{
      put(Parameter.Foo, "BAD");
      put(Parameter.Bar, "GOOD");
      put(Parameter.Baz, "GOOD");
   }});
}};

进入过滤后的地图,其中过滤器将仅包含

Map<String, List<Entry<Parameter, String>>> mapList

结果列表应包含以“ GOOD”作为过滤条件的行。

我无法找出正确的流语法来做到这一点,我知道以下几行:

Map<String, List<Entry<Parameter, String>>> mapList =
    myMap.entrySet().stream().groupingBy(e -> e.getKey()).collect(Collectors.toMap(????)

目前尚不清楚为什么要强调值的EnumMap性质,因为使用该特定Map类型时逻辑不会改变。 您有一个要转换其值的地图,保留了键,这意味着流式处理条目并通过Collectors.toMapCollectors.toMap的方法,让键函数返回原始键,而value函数进行实际转换。

这些值碰巧是一个Map ,您想将其转换为List<Map.Entry> ,这很容易,将条目流式传输并将其收集到List 添加过滤器仅接受"GOOD"值很简单。

现在,很遗憾您在注释中埋入了另一个重要的要求,而不是在问题中指定它。 如果目标地图中根本没有"GOOD"值, "GOOD"忽略外部地图的键。 因此,如果您记得即使没有Streams,Collection API的功能也很强大,那么就需要一个用于外部流操作的过滤器,这并不难。

Map<String, List<Map.Entry<Parameter, String>>> mapList
    = myMap.entrySet().stream()
        .filter(e -> e.getValue().containsValue("GOOD")) // need at least one GOOD there
        .collect(Collectors.toMap(
            Map.Entry::getKey, // keep original keys
            e -> e.getValue().entrySet().stream() // actual conversion
                .filter(sub -> sub.getValue().equals("GOOD")) // GOOD values only
                .collect(Collectors.toList()) // make List<Map.Entry>
            ));

条目已正确分组,仅需要解包和过滤值:

import static java.util.stream.Collectors.*;
...
Map<String, List<Entry<Parameter, String>>> mapList = new HashMap<>();

myMap.forEach((k, v) -> { 
   List<Entry<Parameter, String>> filtered = v.entrySet().stream()
   .filter(e -> e.getValue().equals("GOOD"))
   .collect(toList());

   if(!filtered.isEmpty()) mapList.put(k, filtered);
});

暂无
暂无

声明:本站的技术帖子网页,遵循CC BY-SA 4.0协议,如果您需要转载,请注明本站网址或者原文地址。任何问题请咨询:yoyou2525@163.com.

 
粤ICP备18138465号  © 2020-2024 STACKOOM.COM