Was ist der Unterschied zwischen IQueryable<T>
undIEnumerable<T>
?
Siehe auch Was ist der Unterschied zwischen IQueryable und IEnumerable , der sich mit dieser Frage überschneidet ?
quelle
Was ist der Unterschied zwischen IQueryable<T>
undIEnumerable<T>
?
Siehe auch Was ist der Unterschied zwischen IQueryable und IEnumerable , der sich mit dieser Frage überschneidet ?
Zunächst einmal erweitert die Schnittstelle, so alles , was Sie tun können , mit einem „plain“ , können Sie auch mit einem tun .IQueryable<T>
IEnumerable<T>
IEnumerable<T>
IQueryable<T>
IEnumerable<T>
hat nur eine GetEnumerator()
Methode, die eine zurückgibt, Enumerator<T>
für die Sie ihre MoveNext()
Methode aufrufen können , um eine Folge von T zu durchlaufen .
Was dies nichtIQueryable<T>
hat, sind insbesondere zwei Eigenschaften - eine, die auf einen Abfrageanbieter verweist (z. B. einen LINQ to SQL-Anbieter), und eine andere, die auf einen Abfrageausdruck verweist, der das Objekt als einen zur Laufzeit durchlaufbaren abstrakten Syntaxbaum darstellt, der sein kann vom angegebenen Abfrageanbieter verstanden (zum größten Teil können Sie einem LINQ to Entities-Anbieter keinen LINQ to SQL-Ausdruck geben, ohne dass eine Ausnahme ausgelöst wird).IEnumerable<T>
IQueryable<T>
Der Ausdruck kann einfach ein konstanter Ausdruck des Objekts selbst oder ein komplexerer Baum einer zusammengesetzten Menge von Abfrageoperatoren und Operanden sein. Die IQueryProvider.Execute()
oder IQueryProvider.CreateQuery()
Methoden des Abfrageanbieters werden mit einem an ihn übergebenen Ausdruck aufgerufen , und dann wird entweder ein Abfrageergebnis oder ein anderes IQueryable
zurückgegeben.
AsQueryable()
wandelt nur eine Aufzählung in eine abfragbare um und gibt sie zurück, wenn sie dieIQueryable
Schnittstelle implementiert , andernfalls wird sie in eine eingeschlossenConstantExpression
, auf die in einem zurückgegebenenEnumerableQuery
Objekt verwiesen wird.Der Hauptunterschied besteht darin, dass die LINQ-Operatoren für
IQueryable<T>
Take-Expression
Objekte anstelle von Delegaten, dh die empfangene benutzerdefinierte Abfragelogik, z. B. ein Prädikat oder ein Werteselektor, in Form eines Ausdrucksbaums anstelle eines Delegaten an eine Methode vorliegen.IEnumerable<T>
eignet sich hervorragend für die Arbeit mit Sequenzen, die im Speicher iteriert werden, aberIQueryable<T>
Ermöglicht nicht genügend Arbeitsspeicher wie eine entfernte Datenquelle wie eine Datenbank oder einen Webdienst.Abfrageausführung:
Wenn die Ausführung einer Abfrage "in Bearbeitung" durchgeführt werden soll , ist normalerweise nur der Code (als Code) erforderlich, um jeden Teil der Abfrage auszuführen.
Wenn die Ausführung außerhalb des Prozesses ausgeführt wird , muss die Logik der Abfrage in Daten dargestellt werden, damit der LINQ-Anbieter sie in die entsprechende Form für die Ausführung außerhalb des Speichers konvertieren kann - unabhängig davon, ob es sich um eine LDAP-Abfrage handelt. SQL oder was auch immer.
Mehr in:
IEnumerable<T>
undIQueryable<T>
IEnumerable<T>
vsIQueryable<T>
"IEnumerable
,IQueryable
,IObservable
, undIQbservable
quelle
Dies ist ein schönes Video auf Youtube das zeigt, wie sich diese Schnittstellen unterscheiden, eine Uhr wert.
Nachfolgend finden Sie eine lange beschreibende Antwort darauf.
Der erste wichtige Punkt, an den Sie sich erinnern sollten, ist, dass die
IQueryable
Schnittstelle von erbt.IEnumerable
Was also allesIEnumerable
kann,IQueryable
kann auch.Es gibt viele Unterschiede, aber lassen Sie uns über den einen großen Unterschied diskutieren, der den größten Unterschied macht.
IEnumerable
Die Benutzeroberfläche ist nützlich, wenn Ihre Sammlung mitLINQ
oder Entity Framework geladen wird und Sie einen Filter auf die Sammlung anwenden möchten.Betrachten Sie den folgenden einfachen Code, der
IEnumerable
mit dem Entity Framework verwendet wird. Es wird einWhere
Filter verwendet, um Datensätze abzurufen, derenEmpId
ist2
.Hier wird der Filter auf der Clientseite ausgeführt, auf der sich der
IEnumerable
Code befindet. Mit anderen Worten, alle Daten werden aus der Datenbank abgerufen und dann auf dem Client gescannt und der Datensatz mitEmpId
is abgerufen2
.Aber sehen Sie jetzt den Code unten haben wir geändert
IEnumerable
zuIQueryable
. Es wird eine SQL-Abfrage auf der Serverseite erstellt und nur die erforderlichen Daten werden an die Clientseite gesendet.Also der Unterschied zwischen
IQueryable
undIEnumerable
besteht also darin, wo die Filterlogik ausgeführt wird. Einer wird auf der Clientseite und der andere auf der Datenbank ausgeführt.Wenn Sie also nur mit speicherinterner Datenerfassung arbeiten,
IEnumerable
ist dies eine gute Wahl, wenn Sie jedoch eine Datenerfassung abfragen möchten, die mit der Datenbank verbunden ist. IQueryable ist eine bessere Wahl, da es den Netzwerkverkehr reduziert und die Leistung der SQL-Sprache nutzt.quelle
IEnumerable: IEnumerable eignet sich am besten für die Arbeit mit In-Memory-Sammlungen (oder lokalen Abfragen). IEnumerable bewegt sich nicht zwischen Elementen, sondern ist nur eine Vorwärtssammlung.
IQueryable: IQueryable eignet sich am besten für Remote-Datenquellen wie Datenbanken oder Webdienste (oder Remote-Abfragen). IQueryable ist eine sehr leistungsstarke Funktion, die eine Vielzahl interessanter Szenarien für die verzögerte Ausführung ermöglicht (z. B. Paging- und kompositionsbasierte Abfragen).
Wenn Sie also einfach die In-Memory-Sammlung durchlaufen müssen, verwenden Sie IEnumerable. Wenn Sie die Sammlung wie Dataset und andere Datenquellen bearbeiten möchten, verwenden Sie IQueryable
quelle
Mit einfachen Worten, ein weiterer wesentlicher Unterschied besteht darin, dass IEnumerable eine Auswahlabfrage auf der Serverseite ausführt, Daten auf der Clientseite in den Speicher lädt und dann Daten filtert, während IQueryable eine Auswahlabfrage auf der Serverseite mit allen Filtern ausführt.
quelle
Im wirklichen Leben, wenn Sie ein ORM wie LINQ-to-SQL verwenden
In beiden Fällen wird die Abfrage viermal für die Datenbank ausgeführt, wenn Sie eine Abfrage nicht aufrufen
ToList()
oderToArray()
dann bei jeder Verwendung ausgeführt werden. Wenn Sie beispielsweise eine Abfrage habenIQueryable<T>
und 4 Listenfelder daraus ausfüllen.Auch wenn Sie Ihre Anfrage erweitern:
Dann enthält die generierte SQL mit einem IQueryable "where name =" a ", aber mit einem IEnumerable werden viel mehr Rollen aus der Datenbank zurückgezogen, und die Prüfung x.name =" a "wird von .NET durchgeführt.
quelle
IEnumerable bezieht sich auf eine Sammlung, IQueryable ist jedoch nur eine Abfrage und wird in einem Ausdrucksbaum generiert. Wir führen diese Abfrage aus, um Daten aus der Datenbank abzurufen.
quelle
Der unten erwähnte kleine Test kann Ihnen helfen, einen Aspekt des Unterschieds zwischen
IQueryable<T>
und zu verstehenIEnumerable<T>
. Ich habe diese Antwort aus diesem Beitrag reproduziert, in dem ich versucht habe, Korrekturen zum Beitrag eines anderen hinzuzufügenIch habe folgende Struktur in DB (DDL-Skript) erstellt:
Hier ist das Skript zum Einfügen von Datensätzen (DML-Skript):
Mein Ziel war es nun einfach, die Top 2 Datensätze aus der
Employee
Tabelle in der Datenbank zu erhalten. Ich habe meiner Konsolenanwendung ein ADO.NET-Entitätsdatenmodellelement hinzugefügt, das auf eineEmployee
Tabelle in meiner Datenbank verweist, und mit dem Schreiben von LINQ-Abfragen begonnen.Code für IQueryable Route :
Als ich dieses Programm ausführte, hatte ich auch eine Sitzung des SQL Query-Profilers auf meiner SQL Server-Instanz gestartet. Hier ist die Zusammenfassung der Ausführung:
SELECT TOP (2) [c].[Salary] AS [Salary] FROM [dbo].[Employee] AS [c]
Es ist nur
IQueryable
klug genug, dieTop (2)
Klausel auf der Seite des Datenbankservers selbst anzuwenden, sodass nur 2 von 5 Datensätzen über das Netzwerk übertragen werden. Eine weitere In-Memory-Filterung ist auf der Client-Computerseite überhaupt nicht erforderlich.Code für IEnumerable Route :
Zusammenfassung der Ausführung in diesem Fall:
SELECT [Extent1].[Salary] AS [Salary] FROM [dbo].[Employee] AS [Extent1]
Jetzt werden
IEnumerable
alle 5 in derSalary
Tabelle vorhandenen Datensätze angezeigt und anschließend eine speicherinterne Filterung auf dem Client-Computer durchgeführt, um die beiden besten Datensätze zu erhalten. So wurden unnötigerweise mehr Daten (in diesem Fall 3 zusätzliche Datensätze) über das Kabel übertragen.quelle
Folgendes habe ich in einem ähnlichen Beitrag geschrieben (zu diesem Thema). (Und nein, ich zitiere mich normalerweise nicht, aber das sind sehr gute Artikel.)
"Dieser Artikel ist hilfreich: IQueryable vs IEnumerable in LINQ-to-SQL .
In diesem Artikel heißt es: „Gemäß der MSDN-Dokumentation werden bei IQueryable getätigten Aufrufen stattdessen der interne Ausdrucksbaum erstellt. "Diese Methoden, die IQueryable (Of T) erweitern, führen keine direkte Abfrage durch. Stattdessen besteht ihre Funktionalität darin, ein Ausdrucksobjekt zu erstellen, bei dem es sich um einen Ausdrucksbaum handelt, der die kumulative Abfrage darstellt."
Ausdrucksbäume sind ein sehr wichtiges Konstrukt in C # und auf der .NET-Plattform. (Sie sind im Allgemeinen wichtig, aber C # macht sie sehr nützlich.) Um den Unterschied besser zu verstehen, empfehle ich, die Unterschiede zwischen Ausdrücken und Aussagen in der offiziellen C # 5.0-Spezifikation hier zu lesen . Für fortgeschrittene theoretische Konzepte, die in die Lambda-Rechnung verzweigen, ermöglichen Ausdrücke die Unterstützung von Methoden als erstklassige Objekte. Der Unterschied zwischen IQueryable und IEnumerable konzentriert sich auf diesen Punkt. IQueryable erstellt Ausdrucksbäume, IEnumerable jedoch nicht, zumindest nicht allgemein für diejenigen von uns, die nicht in den geheimen Labors von Microsoft arbeiten.
Hier ist ein weiterer sehr nützlicher Artikel, der die Unterschiede aus Push- / Pull-Perspektive beschreibt. (Mit "Push" vs. "Pull" beziehe ich mich auf die Richtung des Datenflusses. Reaktive Programmiertechniken für .NET und C #
Hier ist ein sehr guter Artikel, der die Unterschiede zwischen Anweisungs-Lambdas und Ausdrucks-Lambdas detailliert beschreibt und die Konzepte der Ausdrucksstress ausführlicher behandelt: Wiederholung von C # -Delegierten, Ausdrucksbäumen und Lambda-Anweisungen im Vergleich zu Lambda-Ausdrücken. . "
quelle
Wir verwenden
IEnumerable
undIQueryable
bearbeiten die Daten, die aus der Datenbank abgerufen werden.IQueryable
erbt vonIEnumerable
,IQueryable
enthält also alleIEnumerable
Funktionen. Der Hauptunterschied zwischenIQueryable
undIEnumerable
besteht darin, dassIQueryable
die Abfrage mit Filtern ausgeführt wird, währendIEnumerable
die Abfrage zuerst ausgeführt wird und dann die Daten basierend auf den Bedingungen gefiltert werden.Eine detailliertere Unterscheidung finden Sie unten:
IEnumerable
IEnumerable
existiert imSystem.Collections
NamespaceIEnumerable
Führen Sie eine Auswahlabfrage auf der Serverseite aus, laden Sie Daten auf einer Clientseite in den Speicher und filtern Sie dann die DatenIEnumerable
eignet sich zum Abfragen von Daten aus speicherinternen Sammlungen wie List, ArrayIEnumerable
ist vorteilhaft für LINQ to Object- und LINQ to XML-AbfragenIQueryable
IQueryable
existiert imSystem.Linq
NamespaceIQueryable
führt serverseitig eine 'Auswahlabfrage' mit allen Filtern ausIQueryable
eignet sich zum Abfragen von Daten aus Sammlungen außerhalb des Speichers (z. B. Remote-Datenbank, Dienst)IQueryable
ist vorteilhaft für LINQ to SQL-AbfragenWird
IEnumerable
also im Allgemeinen für den Umgang mit In-Memory-Sammlungen verwendet, währendIQueryable
es im Allgemeinen zum Bearbeiten von Sammlungen verwendet wird.quelle
Sowohl IEnumerable als auch IQueryable werden verwendet, um die Erfassung von Daten zu speichern und Datenmanipulationsvorgänge durchzuführen, beispielsweise das Filtern der Datenerfassung. Hier finden Sie den besten Unterschied Vergleich mit Beispiel. http://www.gurujipoint.com/2017/05/difference-between-ienumerable-and.html
quelle
IQueryable ist schneller als IEnumerable, wenn es sich um große Datenmengen aus der Datenbank handelt, da IQueryable nur die erforderlichen Daten aus der Datenbank abruft, wobei IEnumerable alle Daten unabhängig von der Notwendigkeit aus der Datenbank abruft
quelle
ienumerable: Wenn wir uns mit Inprocess-Speicher befassen möchten, dh ohne Datenverbindung. iqueryable: Wann mit SQL Server, dh mit Datenverbindungs-Ilist: Operationen wie Objekt hinzufügen, Objekt löschen usw.
quelle