In Anbetracht der Leistung beim Suchen und Löschen von Wörterbuchschlüsseln, da es sich um Hash-Operationen handelt, und angesichts des Wortlauts der Frage, der der beste Weg war, denke ich, dass das Folgende ein vollkommen gültiger Ansatz ist und die anderen meiner Meinung nach etwas zu kompliziert sind.
public static void MergeOverwrite<T1, T2>(this IDictionary<T1, T2> dictionary, IDictionary<T1, T2> newElements)
{
if (newElements == null) return;
foreach (var e in newElements)
{
dictionary.Remove(e.Key); //or if you don't want to overwrite do (if !.Contains()
dictionary.Add(e);
}
}
ODER wenn Sie in einer Multithread-Anwendung arbeiten und Ihr Wörterbuch ohnehin threadsicher sein muss, sollten Sie Folgendes tun:
public static void MergeOverwrite<T1, T2>(this ConcurrentDictionary<T1, T2> dictionary, IDictionary<T1, T2> newElements)
{
if (newElements == null || newElements.Count == 0) return;
foreach (var ne in newElements)
{
dictionary.AddOrUpdate(ne.Key, ne.Value, (key, value) => value);
}
}
Sie können dies dann umbrechen, um eine Aufzählung von Wörterbüchern zu verarbeiten. Unabhängig davon sehen Sie ungefähr ~ O (3n) (alle Bedingungen sind perfekt), da die .Add()
einen zusätzlichen, unnötigen, aber praktisch kostenlosen,Contains()
hinter die Kulissen werfen. Ich denke nicht, dass es viel besser wird.
Wenn Sie zusätzliche Vorgänge für große Sammlungen einschränken möchten, sollten Count
Sie die Größe jedes Wörterbuchs, das Sie zusammenführen möchten, zusammenfassen und die Kapazität des Zielwörterbuchs auf diese festlegen, wodurch die späteren Kosten für die Größenänderung vermieden werden. Das Endprodukt ist also ungefähr so ...
public static IDictionary<T1, T2> MergeAllOverwrite<T1, T2>(IList<IDictionary<T1, T2>> allDictionaries)
{
var initSize = allDictionaries.Sum(d => d.Count);
var resultDictionary = new Dictionary<T1, T2>(initSize);
allDictionaries.ForEach(resultDictionary.MergeOverwrite);
return resultDictionary;
}
Beachten Sie, dass ich mich IList<T>
für diese Methode entschieden habe ... hauptsächlich, weil Sie sich bei der Aufnahme einer Methode IEnumerable<T>
für mehrere Aufzählungen desselben Satzes geöffnet haben. Dies kann sehr kostspielig sein, wenn Sie Ihre Sammlung von Wörterbüchern von einem zurückgestellten LINQ erhalten haben Aussage.
dicA.Concat(dicB).ToDictionary(kvp => kvp.Key, kvp => kvp.Value)