私はスマートなコードのためにラムダ関数を使用する方法を学習しようとしているが、この作品を作るのに苦労しています。
私は2つのリストを持っています。「古い」リストは常に短くまたは「更新リスト」と同じ長さです。私は、「更新リスト」からオブジェクトを取得し、短い「古いリスト」に「古いオブジェクトを」上書きします。リストは、各オブジェクトの一意のフィールドを持っています。
例えば、それは少し新しい版で図書館で本を更新するようなものです。UUID(タイトル+著者)は同じままですが、新しいオブジェクトは、新しい本/オブジェクトを棚に古いものを置き換えます。
私はそれを「長い道のり」を行うと、作ることができる知っているHashMap<MyUniqueFieldInMyObject, MyObject>
し、新しいを取るList<MyUpdatedObjects>
と同じことを行います。
すなわち持っているHashMap<UniqueField, MyOldObject>
とはHashMap<UniqueField, MyUpdatedObject>
、その後、擬似「更新されたオブジェクトは、同じキーを持つエントリを持っている場合は、更新された値で値を上書きする」と古いオブジェクトを反復処理します...
だが...
機能ラムダ文でこれを行うには、「よりよい」短絡方法はありますか?
私はの線に沿って考えていました。
List<MyObject> updatedList;
List<MyObject> oldList;
updatedList.forEach(MyObject -> {
String id = MyObject.getId();
if (oldList.stream().anyMatcher(MyObject ->
MyObject.getId().matches(id)) {
//Do the replacement here? If so...how?
}
}
これは私が失われています場所です!
任意の指導をありがとう。
あなたではなく、新しいリストを作成するよりも、所定の位置にリストを更新したい場合は、使用することができますList.replaceAll
:
oldList.replaceAll(old ->
updateListe.stream()
.filter(updated -> updated.getId().equals(old.getId())
.findFirst()
.orElse(old)
);
この解決策の主な問題は、その複雑さはO(サイズの古い*サイズの更新)であるということです。あなたは「長い道のり」と説明した手法は、古いリスト内のすべてのエントリの全体の最新リストを反復処理することからあなたを守ることができます。
// note that this will throw if there are multiple entries with the same id
Map<String, MyObject> updatedMap = updatedList.stream()
.collect(toMap(MyObject::getId, x->x));
oldList.replaceAll(old -> updatedMap.getOrDefault(old.getId(), old));