web-dev-qa-db-ja.com

Java 8のLambdaでストリームをHashMapに収集します

私はいくつかの関数を使用してフィルタリングする必要があるHashMapを持っています:

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

サイズ= 2の場合、以下が有効である必要があります。

containerBeforeFilter = {1,2,3} -> 1.5, {1,2} -> 1.3
containerAfterFilter = {1,2} -> 1.3

フィルターで関数を適用した後、結果をHashMapに再度収集します。ただし、提案されたメソッド here を適用しようとすると、不正なステートメントが表示されます。

そのため、フィルターの後に適用される次のステートメントは無効です。

.collect(Collectors.toMap((entry) -> entry.getKey(), (entry) -> entry.getValue()));

唯一の基準がいくつかのキーを満たす場合、未変更のマップ値を収集する適切な方法は何でしょうか?

[〜#〜] update [〜#〜]

上記のコードの間違いは、変数mapの型です。 Map.EntryではなくMapにする必要があります。

したがって、機能コードは次のとおりです。

Map<Set<Integer>, Double> map = container.entrySet()
            .stream()
            .filter(k -> k.getKey().size() == size)
            .collect(Collectors.toMap(entry -> entry.getKey(), entry -> entry.getValue()));
12
chao

Collectors.toMapはあなたの例ではstream.collectの型引数を取得せず、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()));
7
wero

を使用してより良いソリューションがあります

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

次のように使用できます。

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));
10
provisota