144 votes

Linq approprié où clauses

J’ai écris une bonne quantité de linq dans ma vie quotidienne, mais pour la plupart des instructions simples. J’ai remarqué que lorsque vous utilisez où les clauses, il y a plusieurs façons de les écrire et ont chacun les mêmes résultats pour autant que je peux dire. Par exemple ;

Semble être équivalent à cela au moins en ce qui concerne les résultats sont :

Donc y a-t-il vraiment une différence autre que de la syntaxe ? Si oui, quelle est le style préféré et pourquoi ?

159voto

Jon Skeet Points 692016

EDIT: LINQ to Objects ne se comportent pas de la façon dont je l'avais prévu. Vous pourriez bien être intéressé par le blog , j'ai juste écrit à ce sujet...


Ils sont différents en termes de ce qui sera appelé - la première est équivalente à:

Collection.Where(x => x.Age == 10)
          .Where(x => x.Name == "Fido")
          .Where(x => x.Fat == true)

wheras ce dernier est équivalent à:

Collection.Where(x => x.Age == 10 && 
                      x.Name == "Fido" &&
                      x.Fat == true)

Maintenant, quelle est la différence qui fait dépendre de la mise en œuvre de l' Where de la demande. Si c'est une base SQL fournisseur, je m'attends à les deux de créer le même SQL. Si c'est dans LINQ to Objects, le deuxième aura moins de niveaux d'indirection (il y a juste deux itérateurs impliqués au lieu de quatre). Si ces niveaux d'indirection sont importants en termes de vitesse est une autre affaire.

Généralement je voudrais utiliser plusieurs where clauses si ils se sentent comme ils représentent significativement différentes conditions (par exemple, l'un est de le faire avec une partie d'un objet, et on est complètement séparé) et un where clause lors de diverses conditions sont étroitement liées (par exemple, la valeur est supérieure à un minimum et de moins de un maximum). Fondamentalement, il est utile de considérer la lisibilité avant tout une légère différence de performances.

79voto

Bala R Points 57552

Le second serait plus efficace, car elle n'a qu'un seul prédicat à évaluer à l'encontre de chaque élément de la collection où, comme dans le premier, c'est l'application du premier prédicat à tous les éléments de la première et le résultat (ce qui est rétréci vers le bas à ce point) est utilisé pour la deuxième prédicat et ainsi de suite. Les résultats se rétrécit vers le bas à chaque passe, mais encore il implique plusieurs passes.

Aussi le chaînage (première méthode) ne fonctionne que si vous êtes ANDing votre prédicats. Quelque chose comme ce x.Age == 10 || x.Fat == true ne fonctionnera pas avec votre première méthode.

15voto

quand je lance

et

contre ma table Customer il sortie la même requête sql

donc en traduction à sql, il n’y a pas de différence et vous déjà avez vu dans les autres réponses comment ils seront convertis à des expressions lambda

14voto

user7116 Points 39829

L’une sera exécutée :

Par opposition à la plus simple (et <strike>beaucoup plus rapide</strike>sans doute plus rapide) :

3voto

David Schmitt Points 29384

Regarder sous le capot, les deux états sera transformé en différents requête représentations. Selon la QueryProvider de Collection, cela pourrait être optimisé loin ou pas.

Quand c'est une linq-to-objet de l'appel, plusieurs clauses where va conduire à une chaîne de IEnumerables qui lisent les uns les autres. À l'aide de la seule clause de la forme permettra de performance ici.

Lorsque le fournisseur sous-jacent traduit dans une instruction SQL, les chances sont bonnes que les deux variantes permettra de créer la même déclaration.

Prograide.com

Prograide est une communauté de développeurs qui cherche à élargir la connaissance de la programmation au-delà de l'anglais.
Pour cela nous avons les plus grands doutes résolus en français et vous pouvez aussi poser vos propres questions ou résoudre celles des autres.

Powered by:

X