C#, Entity Framework: Comment puis-je combiner un .Trouver et .Inclure sur un Objet de Modèle?
Je suis en train de faire la mvcmusicstore pratique tutoriel. J'ai remarqué quelque chose lors de la création de l'échafaudage pour le gestionnaire d'album (ajouter supprimer modifier).
Je veux écrire du code élégamment, donc je suis à la recherche de la propre façon d'écrire cela.
Pour info je suis en train de faire le magasin le plus générique:
Albums = Éléments
Genres = Catégories
Artiste = Marque
Ici est de savoir comment l'index est récupéré (généré par MVC):
var items = db.Items.Include(i => i.Category).Include(i => i.Brand);
Ici est de savoir comment l'élément à supprimer est extrait:
Item item = db.Items.Find(id);
Le premier ramène tous les éléments et les remplit de la catégorie et les modèles de la marque à l'intérieur de l'élément de modèle. La deuxième, ne pas remplir la catégorie et la marque.
Comment puis-je écrire le deuxième à faire de la recherche ET de remplir ce qui est à l'intérieur (de préférence en 1 ligne)... en théorie - quelque chose comme:
Item item = db.Items.Find(id).Include(i => i.Category).Include(i => i.Brand);
- Si quelqu'un à besoin pour ce faire de façon générique dans.net-de base voir ma réponse
Vous devez vous connecter pour publier un commentaire.
Vous devez utiliser
Include()
d'abord, puis de récupérer un objet unique résultant de la requête:...ToList().Find(id)
ou...SingleOrDefault()
à la place. Voir modifié réponse.Dennis réponse est à l'aide de
Include
etSingleOrDefault
. Ce dernier va en aller-retour à la base de données.Une alternative est d'utiliser
Find
, en combinaison avecLoad
, pour le chargement explicite des entités liées...Ci-dessous MSDN exemple:
Bien sûr,
Find
retourne immédiatement sans faire une demande à la banque, si l'entité est déjà chargé par le contexte.Find
donc, si l'entité est présente, il n'y a pas d'aller-retour à la base de données pour l'entité elle-même. MAIS, vous aurez un aller-retour pour chaque relation que vous êtesLoad
ing, alors que laSingleOrDefault
combinaison avecInclude
charges tout en une seule fois.Load
fonction, la relation doit être remplie lorsque les retours d'appel. Donc, si vous appelezLoad
plusieurs fois pour de multiples relations, il y aura un aller-retour à chaque fois. Même pour un seul rapport, si laFind
méthode ne permet pas de trouver de l'entité dans la mémoire, il fait deux voyages: l'un pourFind
et la deuxième pourLoad
. Mais leInclude
.SingleOrDefault
approche des extractions à l'entité et de la relation dans un aller autant que je sache (mais je ne suis pas sûr)N'a pas fonctionné pour moi. Mais je l'ai résolu en faisant comme ceci.
Ne sais pas si c'est un ok de la solution. Mais l'autre Dennis a donné m'a donné un bool erreur dans
.SingleOrDefault(x => x.ItemId = id);
SingleOrDefault(x => x.ItemId = id)
seulement à cause de la mauvaise unique=
au lieu de double==
?Il n'y a pas de véritable moyen facile de filtrer avec une. Mais je suis venu avec une proximité façon à reproduire la fonctionnalité, mais veuillez prendre note de quelques choses pour ma solution.
Ces Solutions vous permet de filtrer de manière générique, sans knowning la clé primaire dans la .net-de base
Trouver est fondamentalement différente parce qu'il obtient de l'entité si elle est présente dans le suivi avant d'Interroger la base de données.
En outre, Il peut filtrer par un Objet de sorte que l'utilisateur n'a pas à connaître la clé primaire.
Cette solution est pour EntityFramework de Base.
Voici quelques méthodes d'extension pour ajouter ce qui vous aidera à filtrer par la clé primaire de sorte
Une fois que vous avez ces méthodes d'extension, vous pouvez filtrer comme suit:
Vous devez lancer IQueryable à DbSet
var dbSet = (DbSet<Item>) db.Set<Item>().Include("");
return dbSet.Find(id);