web-dev-qa-db-fra.com

EF ICollection Vs List Vs IEnumerable Vs IQueryable

donc, mon modèle EF a des relations et selon ce que j'ai vu dans les exemples, ces relations devraient être faites avec les propriétés virtuelles de ICollection.

Exemple:

 public class Task
    {
        public int Id { get; set; }
        public string Description { get; set; }
        public virtual ICollection<SubTask>  { get; set; }
    }

J'ai lu quelque part que je devrais utiliser IEnumerable pour empêcher l'exécution différée, est-ce correct? Cela signifie que si mes méthodes DAL retournent IEnumerable, toujours de IQueryable, le SQL sera exécuté à ce moment, et non au moment où j'appelle .TOList dans la page Web.

Alors, quelle est la meilleure pratique? Que dois-je retourner? IEnumerable, List ?, IList, ICollection?

tHX

49
Luis Valencia

IQueryable :

  • La requête n'est pas exécutée tant que vous n'avez pas vraiment itéré les éléments, peut-être en faisant une .ToList() ou une foreach. Ce qui signifie que vous pouvez toujours ajouter des filtres, comme une Where().
  • Étend IEnumerable

IEnumerable :

  • Liste d'éléments en avant uniquement. Vous ne pouvez pas accéder à "l'élément 4" sans passer les éléments 0-3.
  • Liste en lecture seule, vous ne pouvez pas y ajouter ou en supprimer.
  • Peut encore utiliser l'exécution différée (IQueryable est toujours un IEnumerable).

IList :

  • Accès aléatoire à la liste complète
  • Probablement entièrement en mémoire (pas d'exécution différée, mais qui sait quelle classe exacte cela implémente-t-il?)
  • Prend en charge l'ajout et la suppression
  • Étend IEnumerable et ICollection

ICollection :

  • Est entre IEnumerable et IList.
  • Étend IEnumerable

Ce qui est "le meilleur" dépend de vos besoins. Habituellement, bien qu'un IEnumerable soit "assez bon" si vous ne souhaitez afficher que des éléments. Utilisez au moins toujours la variante générique.

63
Hans Kesting

Une autre différence en cas d'EF est que l'IEnumerable n'exécute pas la requête dans la base de données jusqu'à ce que vous énumériez vraiment la liste. Alors que l'IList exécutera la requête et récupérera les éléments en mémoire. J'ai eu un comportement étrange avec la mise en cache. Chaching l'IEnumarable n'a pas stocké les éléments mais plutôt l'énumération non récupérée, chaque fois que j'appelais le cache et récupérais l'énumération dans un but, il allait à la base de données et exécutait la requête, donc la mise en cache était inutile. Mais un ToList () sur l'énumération a récupéré les éléments et stocké les éléments dans le cache, donc seulement 1 voyage vers la base de données pour cela. En savoir plus dans cet article: http://www.dailycode.info/BlogV2/post/entityframework-adding-ienumerable-to-cache

1
Mark