変換したい:
Map<String, Map<String, List<Map<String, String>>>> inputMap
に:
Map<String, Map<String, CustomObject>> customMap
inputMap
は設定で提供されており、準備ができていますが、customMap
形式にする必要があります。 CustomObjectは、関数で数行のコードを使用してList<Map<String, String>>
から派生します。
入力マップを反復し、customMapでキー値をコピーする通常の方法を試しました。 Java 8または他のショートカットを使用してそれを行う効率的な方法はありますか?
Map<String, Map<String, List<Map<String, String>>>> configuredMap = new HashMap<>();
Map<String, Map<String, CustomObj>> finalMap = new HashMap<>();
for (Map.Entry<String, Map<String, List<Map<String, String>>>> attributeEntry : configuredMap.entrySet()) {
Map<String, CustomObj> innerMap = new HashMap<>();
for (Map.Entry<String, List<Map<String, String>>> valueEntry : attributeEntry.getValue().entrySet()) {
innerMap.put(valueEntry.getKey(), getCustomeObj(valueEntry.getValue()));
}
finalMap.put(attributeEntry.getKey(), innerMap);
}
private CustomObj getCustomeObj(List<Map<String, String>> list) {
return new CustomObj();
}
私見ストリーミングはそれほど悪い考えではありません。悪いツールはありません。それはあなたがそれらをどのように使っているかに依存します。
この特定のケースでは、繰り返しパターンをユーティリティメソッドに抽出します。
public static <K, V1, V2> Map<K, V2> transformValues(Map<K, V1> map, Function<V1, V2> transformer) {
return map.entrySet()
.stream()
.collect(toMap(Entry::getKey, e -> transformer.apply(e.getValue())));
}
上記の方法は、どのアプローチを使用しても実装できますが、Stream API
はここでかなりよく合います。
ユーティリティメソッドを定義すると、次のように簡単に使用できます。
Map<String, Map<String, CustomObj>> customMap =
transformValues(inputMap, attr -> transformValues(attr, this::getCustomObj));
実際の変換は事実上1つのライナーです。したがって、適切なJavaDoc
for transformValues
メソッドを使用すると、結果コードはかなり読みやすく、保守しやすくなります。
ストリーミングはできますが、読みやすくはありません。少なくとも私には。したがって、メソッドがある場合:
static CustomObject fun(List<Map<String, String>> in) {
return .... // whatever processing you have here
}
Java-8
構文、ただし別の形式:
Map<String, Map<String, CustomObject>> customMap = new HashMap<>();
inputMap.forEach((key, value) -> {
value.forEach((innerKey, listOfMaps) -> {
Map<String, CustomObject> innerMap = new HashMap<>();
innerMap.put(innerKey, fun(listOfMaps));
customMap.put(key, innerMap);
});
});
内部マップをimmutable
にできれば、さらに短くすることができます。
inputMap.forEach((key, value) -> {
value.forEach((innerKey, listOfMaps) -> {
customMap.put(key, Collections.singletonMap(innerKey, fun(listOfMaps)));
});
});
Collectors.toMap
は、次のような外部レベルと内部レベルの両方のエントリに使用します。
Map<String, Map<String, CustomObj>> finalMap = configuredMap.entrySet()
.stream()
.collect(Collectors.toMap(Map.Entry::getKey,
attributeEntry -> attributeEntry.getValue().entrySet()
.stream()
.collect(Collectors.toMap(Map.Entry::getKey,
valueEntry -> getCustomeObj(valueEntry.getValue())))));