Was ist am schnellsten (und am wenigsten ressourcenintensiv), um zwei massive (> 50.000 Elemente) zu vergleichen und als Ergebnis zwei Listen wie die folgenden zu haben:
- Elemente, die in der ersten Liste angezeigt werden, jedoch nicht in der zweiten
- Elemente, die in der zweiten Liste angezeigt werden, jedoch nicht in der ersten
Derzeit arbeite ich mit der Liste oder IReadOnlyCollection und löse dieses Problem in einer Linq-Abfrage:
var list1 = list.Where(i => !list2.Contains(i)).ToList();
var list2 = list2.Where(i => !list.Contains(i)).ToList();
Aber das funktioniert nicht so gut, wie ich es gerne hätte. Haben Sie eine Idee, dies schneller und weniger ressourcenintensiv zu machen, da ich viele Listen verarbeiten muss?
Equals(object)
und / oder implementiertIEquatable<T>
, sollte dies in Ordnung sein.IEquatable<T>
Implementierung oder dieobject.Equals(object)
Methode verwendet. Es hört sich so an, als ob Sie eine neue Frage mit einem minimal reproduzierbaren Beispiel erstellen sollten - wir können Dinge in Kommentaren nicht wirklich diagnostizieren.Effizienter wäre
Enumerable.Except
:Diese Methode wird mithilfe der verzögerten Ausführung implementiert. Das heißt, Sie könnten zum Beispiel schreiben:
Es ist auch effizient, da es intern a verwendet
Set<T>
, um die Objekte zu vergleichen. Es funktioniert, indem zuerst alle unterschiedlichen Werte aus der zweiten Sequenz gesammelt und dann die Ergebnisse der ersten gestreamt werden, um zu überprüfen, ob sie zuvor noch nicht gesehen wurden.quelle
Set<T>
wird aus der zweiten Sequenz erstellt (dh es wird vollständig iteriert und gespeichert), und dann werden Elemente ausgegeben, die aus der ersten Sequenz hinzugefügt werden können.Where
teilweise verzögert wird, weillist.Where(x => x.Id == 5)
der Wert der Zahl5
zu Beginn gespeichert und nicht träge ausgeführt wird.Dies funktioniert für alle primitiven Datentypen. Wenn Sie es für benutzerdefinierte Objekte verwenden müssen, müssen Sie es implementieren
IEqualityComparer
Definiert Methoden zur Unterstützung des Vergleichs von Objekten auf Gleichheit.
quelle
SequenceEqual
einfach istbool
. Das OP möchte zwei Ergebnislisten - und beschreibt, was sie in Bezug auf festgelegte Operationen wollen: "Elemente, die in der ersten Liste angezeigt werden, aber nicht in der zweiten". Es gibt keinen Hinweis darauf, dass die Reihenfolge relevant ist, während SequenceEqual dies für relevant hält. Dies scheint eine ganz andere Frage zu beantworten.Wenn Sie möchten, dass bei den Ergebnissen die Groß- und Kleinschreibung nicht berücksichtigt wird, funktioniert Folgendes:
firstNotSecond
würde b1.dll enthaltensecondNotFirst
würde b2.dll enthaltenquelle
Nicht für dieses Problem, aber hier ist ein Code zum Vergleichen von Listen für gleich und nicht! identische Objekte:
quelle
Except
versuche es so:
quelle
Manchmal muss man nur wissen, ob zwei Listen unterschiedlich sind und nicht, was diese Unterschiede sind. In diesem Fall sollten Sie diese Erweiterungsmethode zu Ihrem Projekt hinzufügen. Beachten Sie, dass Ihre aufgelisteten Objekte IEquatable implementieren sollten!
Verwendung:
Was auch immer die
Component
Klasse ist, die hier gezeigten Methoden fürCar
nahezu identisch implementiert werden.Es ist sehr wichtig zu beachten, wie wir GetHashCode geschrieben haben. Um richtig umzusetzen
IEquatable
,Equals
undGetHashCode
muss auf der Instanz Eigenschaften in eine logisch kompatibelen Weise.Zwei Listen mit demselben Inhalt sind immer noch unterschiedliche Objekte und erzeugen unterschiedliche Hash-Codes. Da diese beiden Listen gleich behandelt werden sollen, müssen wir
GetHashCode
für jede Liste den gleichen Wert erzeugen. Dies können wir erreichen, indem wir den Hashcode an jedes Element in der Liste delegieren und alle mit dem standardmäßigen bitweisen XOR kombinieren. XOR ist auftragsunabhängig, daher spielt es keine Rolle, ob die Listen unterschiedlich sortiert sind. Es ist nur wichtig, dass sie nur gleichwertige Mitglieder enthalten.Hinweis: Der seltsame Name bedeutet, dass die Methode die Reihenfolge der Elemente in der Liste nicht berücksichtigt. Wenn Sie sich für die Reihenfolge der Elemente in der Liste interessieren, ist diese Methode nichts für Sie!
quelle
Ich habe diesen Code verwendet, um zwei Listen mit Millionen von Datensätzen zu vergleichen.
Diese Methode wird nicht viel Zeit in Anspruch nehmen
quelle
Wenn nur ein kombiniertes Ergebnis benötigt wird, funktioniert dies auch:
Dabei ist T der Typ des Listenelements.
quelle
Mag lustig sein, funktioniert aber für mich
string.Join ("", List1)! = string.Join ("", List2)
quelle
Ich denke, dies ist eine einfache Möglichkeit, zwei Listen Element für Element zu vergleichen
quelle
Dies ist die beste Lösung, die Sie gefunden haben
quelle
List<T>
für jedes Element in ein neues erstelltlist1
. Auch das Ergebnis wird aufgerufen,list3
wenn es nicht a istList<T>
.