亚洲在线久爱草,狠狠天天香蕉网,天天搞日日干久草,伊人亚洲日本欧美

為了賬號安全,請及時綁定郵箱和手機立即綁定
已解決430363個問題,去搜搜看,總會有你想問的

使用 EF 將 T 從 DbSet<T> 映射到數據庫內部表示

使用 EF 將 T 從 DbSet<T> 映射到數據庫內部表示

C#
慕俠2389804 2022-11-22 15:48:20
我是 .NET 和 Entity Framework 的初學者,只是一個關于映射的問題,假設我們有 Recipes 類,其屬性是 Ingredient,所以我們有兩個類 Recipes 和 Ingredient。我們通過以下方式進行映射:public DbSet<Recipe> Recipes { get; set; }因此 EF 將檢查 Recipe 的屬性并創建一個 Recipes 表,最終它將找到 Ingredient 作為屬性,因此它將創建一個 Ingredient 表。到目前為止它似乎很簡單,但這是一個非常簡單的結構,所以我們知道 Recipes 包含 Ingredient,所以我們不這樣做public DbSet<Recipe> Recipes { get; set; }public DbSet<Ingredient> Ingredient { get; set; } //duplicated 但想象一下,在一個復雜的應用程序中,我們可能有數百個類,所以當我們這樣做時public DbSet<T> T{ get; set; }public DbSet<U> U{ get; set; }public DbSet<V> V{ get; set; }...T 可能包含 U 作為屬性,而 U 可能包含 V 作為屬性,因此我們只需要編寫如下代碼:public DbSet<T> T{ get; set; }所以我很困惑,我們應該在 DbContext 中包含所有類嗎?如果我們這樣做,將會有重復的聲明,但如果我們不這樣做,我們可能會丟失映射。所以我想我們只是為所有類做 tat 并期望 EF 足夠聰明以忽略重復的東西?
查看完整描述

3 回答

?
慕姐4208626

TA貢獻1852條經驗 獲得超7個贊

EF 足夠聰明,不會創建重復的表,最好將DbSet<>.

當你有一個帶有名稱的類Ingredient并且你在其中引用它時Recept,將只有一個帶有名稱Ingredient的表并且你不能有兩個具有相同名稱的表所以即使你想要也不會創建重復的表。


查看完整回答
反對 回復 2022-11-22
?
HUX布斯

TA貢獻1876條經驗 獲得超6個贊

正如您已經說過的,EF 將Ingredient在屬性中查找類型Recipe并創建Ingredients表。這意味著,Ingredients即使您省略了,也會創建該表public DbSet<Ingredient> Ingredient { get; set; }。然而,僅僅因為你不需要public DbSet<Ingredient> Ingredient { get; set; },并不意味著你不能擁有它。您可以隨意包含它,它不會造成任何傷害,也不會創建任何副本。


添加public DbSet<Ingredient> Ingredient { get; set; }到您的允許您直接從上下文DbContext訪問條目:Ingredient


MyContext context = ...

var ingredients = context.Ingredients;


否則,您將不得不通過屬性訪問Ingredient條目:Recipes


MyContext context = ...

var recipe = context.Recipes...;

var ingredients = recipe.Ingredients;

摘要:什么時候應該將類包含在 DbContext 中?

  • 當該類未被屬于DbContext. 將類添加到DbContext將確保它已映射。

  • 當您希望能夠直接從 DbContext 實例訪問該類的條目時。例如var ingredients = context.Ingredients

  • 當您想確保該類將被映射,并且不想依賴它被其他映射類引用時。

因此,要回答您的問題“我們應該在 DbContext 中包含所有類嗎?” : 你可以,這是完全好的方法。這樣您將確保所有類(您想要映射)都將被映射,而不必依賴于它們被其他類引用。


查看完整回答
反對 回復 2022-11-22
?
紅顏莎娜

TA貢獻1842條經驗 獲得超13個贊

您必須知道您的 dbContext 代表您的數據庫。DbSets 表示數據庫中的表


在實體框架中,表的列由類的非虛擬屬性表示。虛擬屬性表示表之間的關系(一對多,多對多,......)


您的數據庫將有Recipes和Ingredient。EveryRecipe將有零個或多個Ingredients,而 everyIngredient用于零個或多個Recipes:一個簡單的多對多關系。


您將擁有表Recipes和Ingredients,因此您的 dbContext 將擁有DbSets它們:


class MyDbContext : DbContext

{

    public DbSet<Recipe> Recipes {get; set;}

    public DbSet<Ingredient> Ingredients {get; set;}

}


class Recipe

{

    public int Id {get; set;}  // primary key

    ...                        // other columns


    // every Recipe has zero or more ingredients (many-to-many)

    public virtual ICollection<Ingredient> Ingredients {get; set;}

}


class Ingredient

{

    public int Id {get; set;}  // primary key

    ...                        // other columns


    // every Ingredient is used in zero or more Recipes( many-to-many)

    public virtual ICollection<Recipe> Recipes {get; set;}

}

因為我virtual兩邊都用了,Recipes和Ingredients,entity framework可以檢測到我設計的是多對多。實體框架甚至會為我創建一個聯結表,我不必聲明它。


// Fetch all Desserts with their Bitter ingredients

var desertsWithoutSugar = myDbContext.Recipes

    .Where(recipe => recipy.Type == RecipyType.Dessert)

    .Select(recipe => new

    {

        // select only the properties that I plan to use:

        Id = recipe.Id,

        Name = recipe.Name,

        ...

        // not needed: you know the value: Type = recipe.Type


        Ingredients = recipe.Ingredients

           .Where(ingredient => ingredient.Taste == Taste.Bitter)

           .Select(ingredient => new

           {

               // again: only the properties you plan to use

               Id = ingredient.Id,

               Name = ingredient.Name,

           })

           .ToList(),

     })

實體框架了解您的多對多關系,并且足夠聰明,可以檢測到三個表(包括連接表)需要(組)連接。


如果你想設計一個一對多的關系,例如一個學校和他的學生,你virtual ICollection可以在一側聲明唯一。另一方獲得外鍵。這是您表中的一列,因此是非虛擬的


class School

{

    public int Id {get; set;}

    ...                     


    // every School has zero or more Students (one-to-many)

    public virtual ICollection<Student> Students {get; set;}

}

class Student

{

    public int Id {get; set;}

    ...   


    // Every Student studies at one School, using foreign key

    public int SchoolId {get; set;}

    public virtual School School {get; set;}

}

public SchoolContext : DbContext

{

    public DbSet<School> Schools {get; set;}

    public DbSet<Student> Students {get; set;}

}

根據我的經驗,由于我使用實體框架,我幾乎不必再進行 (Group-)join,我使用集合:


給我所有的學校和他們的學生


var Result = dbContext.Schools

    .Where(school => ...)

    .Select(school => new

    {

        Id = school.Id,

        ...


        Students = school.Students

            .Where(student => ...)

            .Select(student => new

            {

                 Id = student.Id,

                 ...

            })

            .ToList(),

    });

類似的:給我所有學生和他們就讀的學校


查看完整回答
反對 回復 2022-11-22
  • 3 回答
  • 0 關注
  • 156 瀏覽

添加回答

舉報

0/150
提交
取消
微信客服

購課補貼
聯系客服咨詢優惠詳情

幫助反饋 APP下載

慕課網APP
您的移動學習伙伴

公眾號

掃描二維碼
關注慕課網微信公眾號