代码之家  ›  专栏  ›  技术社区  ›  user1578872

JAVA 8地图中的Strm过滤器映射图,字符串,map <字符串,雇员>

  •  4
  • user1578872  · 技术社区  · 6 年前

    如何过滤 Map<String,Map<String,Employee>> 使用Java 8过滤器?

    只有当列表中的任何员工的字段值gender=“m”时,我才必须进行筛选。

    输入:

    map<string,map<string,employee>>

    输出:

    map<string,map<string,employee>>

    筛选条件:

    Employee.genter = "M"

    另外,如果过滤结果为空,我必须返回空映射。

    我试过下面的方法,但效果不理想。只有当所有员工都具有“M”性别时,才会返回。

    tempCollection.entrySet().stream()
                            .filter(i -> i.getValue().entrySet().stream().allMatch(e-> "M".equals(e.getValue().getGender())))
                            .collect(Collectors.toMap(Map.Entry::getKey, Map.Entry::getValue));
    
    5 回复  |  直到 6 年前
        1
  •  1
  •   Naman    6 年前

    您可以简单地迭代键值对并按如下方式过滤:

    Map<String, Map<String, Employee>> output = new HashMap<>();
    tempCollection.forEach((k, v) -> {
        if (v.values().stream().anyMatch(i -> "M".equals(i.getGender()))) {
            output.put(k, v.entrySet()
                    .stream()
                    .filter(i -> "M".equals(i.getValue().getGender()))
                    .collect(toMap(Map.Entry::getKey, Map.Entry::getValue)));
        }
    });
    
        2
  •  1
  •   Tordek    6 年前

    函数 allMatch 仅当流中的每个元素与谓词匹配时才匹配;您可以使用 anyMatch 如果任何元素与谓词匹配,则匹配:

    tempCollection.entrySet().stream()
                            .filter(i -> i.getValue().entrySet().stream().anyMatch(e-> "M".equals(e.getValue().getGender())))
                            .collect(Collectors.toMap(Map.Entry::getKey, Map.Entry::getValue));
    
        3
  •  1
  •   Ousmane D.    6 年前

    好像你想要的是 Entry<String,Map<String,Employee>> 如果有任何员工的性别为“M”,那么过滤内部 Map<String,Employee> 只包含性别为“M”的条目。

    在这种情况下,你可以 filter 随着 anyMatch 第一个标准。此外,在收集阶段,您可以在内部映射上应用过滤:

    tempCollection.entrySet().stream()
                .filter(i -> i.getValue().values().stream().anyMatch(e -> "M".equals(e.getGender())))
                .collect(toMap(Map.Entry::getKey,
                        v -> v.getValue().entrySet().stream()
                                .filter(i -> "M".equals(i.getValue().getGender()))
                                .collect(toMap(Map.Entry::getKey, Map.Entry::getValue))));
    
        4
  •  1
  •   Ravindra Ranwala    6 年前

    你可以这样做,

    Map<String, Map<String, Employee>> maleEmpMap = tempCollection.entrySet().stream()
        .map(e -> new AbstractMap.SimpleEntry<>(e.getKey(),
            e.getValue().entrySet().stream().filter(emp -> "M".equals(emp.getValue().getGender()))
                    .collect(Collectors.toMap(Map.Entry::getKey, Map.Entry::getValue))))
        .collect(Collectors.toMap(Map.Entry::getKey, Map.Entry::getValue));
    

    从外部映射中获取每个映射条目,并使用相同的键和新构造的嵌套映射创建一个新的映射条目,该映射条目具有相同的键,并且只有男性员工作为其值。最后将所有匹配的条目收集到一个新的外部映射中。这将优雅地处理您在上面的问题语句中提到的空场景。

        5
  •  0
  •   Hadi Jeddizahed    6 年前

    另一种方法是:

    map.values()
         .removeIf(entry->entry.values().stream().anyMatch(e -> !"M".equals(e.getGender())));
    
    map.entrySet()
        .removeIf(entry->entry.getValue().size() == 0);