使用Java 8中的Lambda将流收集到HashMap中

cha*_*hao 13 java lambda hashmap

我有一个HashMap,我需要使用一些函数进行过滤:

HashMap<Set<Integer>, Double> container
Map.Entry<Set<Integer>, Double> map = container.entrySet()
            .stream()
            .filter(k -> k.getKey().size() == size)
Run Code Online (Sandbox Code Playgroud)

对于size = 2,以下内容应该有效:

containerBeforeFilter = {1,2,3} -> 1.5, {1,2} -> 1.3
containerAfterFilter = {1,2} -> 1.3
Run Code Online (Sandbox Code Playgroud)

在过滤器中应用函数后,我想再次将结果收集到HashMap中.但是,当我尝试应用此处建议的方法时,我会收到非法声明.

因此,在过滤器之后应用的以下语句是非法的:

.collect(Collectors.toMap((entry) -> entry.getKey(), (entry) -> entry.getValue()));
Run Code Online (Sandbox Code Playgroud)

收集未更改的地图值的正确方法是什么,唯一的标准是满足某些关键?

UPDATE

上面代码中的错误是变量的类型map.它应该是Map而不是Map.Entry.

所以功能代码是:

Map<Set<Integer>, Double> map = container.entrySet()
            .stream()
            .filter(k -> k.getKey().size() == size)
            .collect(Collectors.toMap(entry -> entry.getKey(), entry -> entry.getValue()));
Run Code Online (Sandbox Code Playgroud)

pro*_*ota 12

有一个更好的解决方案

toMap(Function<? super T, ? extends K> keyMapper,
                            Function<? super T, ? extends U> valueMapper,
                            BinaryOperator<U> mergeFunction,
                            Supplier<M> mapSupplier)
Run Code Online (Sandbox Code Playgroud)

您可以这样使用它:

HashMap<Set<Integer>, Double> map = container.entrySet()
    .stream()
    .filter(k -> k.getKey().size() == size)
    .collect(Collectors.toMap(Map.Entry::getKey, Map.Entry::getValue, (prev, next) -> next, HashMap::new));
Run Code Online (Sandbox Code Playgroud)

  • @Shyam,您可以在 Javadocs 中找到解释:`Map.Entry::getKey` 等于 `entry -&gt; entry.getKey()` - **keyMapper** 映射函数以生成键 `Map.Entry::getValue` 等于到 `entry -&gt; entry.getValue()` - **valueMapper** 映射函数以产生值 `(prev, next) -&gt; next` - **mergeFunction** 合并函数,用于解决与相同的键,提供给 Map.merge(Object, Object, BiFunction) `HashMap::new` 等于 `() -&gt; new HashMap&lt;&gt;()` - **mapSupplier** 函数返回一个新的空 Map结果将插入其中 (2认同)

wer*_*ero 8

似乎Collectors.toMap没有获取stream.collect示例中的类型参数,只返回a Map<Object,Object>.

作为一种变通方法,您可以自己创建结果映射,并在最后一个流步骤中将过滤后的条目添加到结果映射中:

Map<Set<Integer>, Double> result = new HashMap<>();
container.entrySet()
    .stream()
    .filter(entry -> entry.getKey().size() == size)
    .forEach(entry -> result.put(entry.getKey(), entry.getValue()));
Run Code Online (Sandbox Code Playgroud)