2016-05-30 2 views
0

S'il vous plaît jeter un oeil sur le code suivant:pré-traitement chaque élément dans un <T> IQueryable dans LINQ aux objets

var list = new List<MyClass>(); 
... 
var selection = list 
    .Preprocess() 
    .Where(x => x.MyProperty = 42) 
    .ToList(); 

Je veux mettre en œuvre Preprocess de telle manière qu'il puisse traiter chaque élément sélectionné par le prédicat qui suit. Donc, si list contient des milliers d'objets, je ne veux pas que Preprocess les traite tous, mais seulement ceux qui sont sélectionnés par la clause Where.

Je sais que cela semble être préférable de déplacer Preprocess à la fin de la requête, mais j'ai mes raisons pour le faire de cette façon.

Est-ce possible avec IQueryable<T>? Ou se comporte-t-il comme IEnumerable, où tout le pipeline LINQ-to-objects est strictement séquentiel?

+0

Je dirais d'abord que ce que vous demandez est impossible, car un article LINQ comme celui-ci ne sait jamais ce qui vient après. Une façon différente de l'écrire serait: 'var preprocessed = list.Preprocess(); var whereResult = pré-traité.Where(); var selection = whereResult.ToList(); '. Lorsque listé de cette façon, vous pouvez voir que toute déclaration n'a jamais connaissance de l'instruction suivante. – GTHvidsten

+0

Pourriez-vous avoir la méthode de pré-traitement prendre le prédicat de sélecteur à la place: Preprocess (x => x.MyProperty == 42)? – sondergard

+1

Par intérêt, quelles sont ces raisons pour ne pas mettre juste pré-traitement après Où? – Evk

Répondre

1

Pour vos besoins, IQueryable n'est pas différent de IEnumerable, ce qui est, comme vous l'avez dit, purement séquentiel. Immédiatement après avoir appelé Where(), il n'y a effectivement aucune trace de la "collection" d'origine.

Maintenant, vous pourrait théoriquement faire ce que vous voulez, mais cela nécessiterait de rouler "votre propre LINQ". Preprocess() pourrait renvoyer une sorte de PreprocessedEnumerable, tous les opérateurs personnalisés y attacheraient et le ToList() final fera la réorganisation des appels.