Dictionary Aggreation/Merge



  • Hallo Leute,

    ich möchte On-Fly via Enumerator 2 Dictionaries konsolidieren:

    private IEnumerable<KeyValuePair<string, string>> Aggregate()
            {
                // keys already provided
                var keys = new HashSet<string>();
    
                // first return the local overrides
                foreach (var keyValuePair in DictA)
                {
                    keys.Add(keyValuePair.Key);
                     yield return keyValuePair;
                }
    
                //add the template, if it not overriden
                foreach (var keyValuePair in DictB)
                {
                    if (keys.Contains(keyValuePair.Key))
                        continue;
                    keys.Add(keyValuePair.Key);
                    yield return keyValuePair;
                }
            }
    

    das bedeudet wenn Key X bei DictA schon zurückgeben wurde, und der Key in DictB drin is, soll dieser geskippt werden..
    das ganz soll performant sein, meine erste Idee war diese hier.

    Frage: 1: Ist yield return performant (is halt schön on-fly)
    Frage 2: Gbit es ne performantere Lösung wie ich mir das überlegt habe?

    Danke für die kommenden Eindrücke;)



  • Und warum verwendest du dann ein zusätzliches HashSet? Dictionary<K,V>.ContainsKey hat schon approximativ O(1):

    Remarks

    This method approaches an O(1) operation.

    Die Rückgabe mittels yield ist der bevorzugte Weg, gerade wenn evtl. weitere Linq-Operationen darauf erfolgen (insb. wenn z.B. nur First() bzw. FirstOrDefault() o.ä. danach aufgerufen wird).



  • @Th69 sagte in Dictionary Aggreation/Merge:

    Und warum verwendest du dann ein zusätzliches HashSet? Dictionary<K,V>.ContainsKey hat schon approximativ O(1):

    ja ich mach das ganze jetzt mit ner ConcurrentDictionary<string,X> und AddOrUpdate statt wobei mir gerade einfällt
    Dictionary<string, X> und this["X"] = y ginge auch

    hmm evtl. is die letztere variante schneller.. weil die obere ja ehr über mehrere threads notwendig ist... was ich nich brauche..

    EDIT: Ok, die ConcurrentDictionary ist bei update bzw. indexer zuweisung im factor 3 langsamer...



  • Du brauchst überhaupt keine zusätzliche Datenstruktur: entferne die keys.Add-Anweisungen und verwende in der unteren Schleife if (DictA.ContainsKey(keyValuePair.Key)).

    bzw. noch einfacher in der unteren Schleife:

    if (!DictA.ContainsKey(keyValuePair.Key)
       yield return keyValuePair;
    

    (also continue entfernt)



  • @Th69 sagte in Dictionary Aggreation/Merge:

    Du brauchst überhaupt keine zusätzliche Datenstruktur: entferne die keys.Add-Anweisungen und verwende in der unteren Schleife if (DictA.ContainsKey(keyValuePair.Key)).
    bzw. noch einfacher in der unteren Schleife:
    if (!DictA.ContainsKey(keyValuePair.Key)
    yield return keyValuePair;

    (also continue entfernt)

    ahhh.. gute Idee..danke



  • Darauf hättest du aber auch selber kommen können (KISS). 😉


Anmelden zum Antworten