• Entity Framework Core 简明教程(3)- 关系处理


    在数据库层面,表之间关系,通过主键、外键来实现,基于约束 (constraint) 和数据完整性来制约。 在 EF Core 技术层面,并不是简单地与数据库这些关系和约束对应,EF Core 有它自己的机制。本篇介绍 EF core 在处理表关系方面的典型技术点。为了理解的方便,示例数据库只包含两个表:Articles (文章)和 Comments (文章评论)。很明显,Articles 和 Comments 是一对多关系(一篇文章存在多条评论论)。在数据库中,Comments 表的 Id 字段是外键,指向 Articles 表的 主键 Id 字段。一对多关系是数据表最重要的关系。

    数据库中的关系

    请添加图片描述

    请添加图片描述

    对象模型中的关系

    在 EF Core 中,我们在实体类中定义模型的关系,一般通过导航属性来实现。比如刚才的表模型,在 Articles 实体中, Comments 属性是一个 List,表达 Article 含有多条 Comment。

    请添加图片描述
    当然,这只是 EF Core 提供的的一种实现方式,也可以在 Comments 实体中定义导航属性,指向 Articles 实体。在两个类中同时定义也是可以的。

    请添加图片描述

    注意,这里并不需要显示定义 ArticleId 字段来标识 Comments 表的外键。

    EF Core 关系映射

    EF Core 中关系映射,最基本的内容包括:

    • 为每一个实体 (entity) 添加主键
    • 为实体添加外键 (如果有的话)
    • 通过主键外键定义两个实体的参照关系 (能够清晰地体现出一对多)

    请添加图片描述
    (示例为在多的一方定义)

    关系表的增删改查

    刚才的示例中,在 Articles 实体中和 Comments 实体中,都定义了导航属性。这样我们可以很方便的进行 Create 操作。示例方式一:利用 Articles 实体的导航属性:

    [TestMethod]
    public void TestInsert1()
    {
        var a1 = new Article 
        { 
            Title = ".net下主要ORM框架",
            Content = "xxxxx"
        };
    
        a1.Comments.Add(new Comment { CommentContent = "非常赞"});
        a1.Comments.Add(new Comment { CommentContent = "强烈支持"});
    
        using var context = new AppDbContext();
        context.Articles.Add(a1);
        context.SaveChanges();
    }
    
    • 1
    • 2
    • 3
    • 4
    • 5
    • 6
    • 7
    • 8
    • 9
    • 10
    • 11
    • 12
    • 13
    • 14
    • 15
    • 16

    注意到:不需要显式为 Comment 实体的 Article 属性赋值

    示例新增方式二:利用 Comment 实体的导航属性:

    [TestMethod]
    public void TestInsert2()
    {
        var a1 = new Article
        {
            Title = "EFCore 从入门到精通",
            Content = "EFCore"
        };
    
        var c1 = new Comment { 
            CommentContent = "这篇文章真不错",
            Article = a1
        };
    
        var c2 = new Comment
        {
            CommentContent = "这篇文章写的不错呀",
            Article = a1
        };
    
        a1.Comments.Add(c1);
        a1.Comments.Add(c2);
    
        using var context = new AppDbContext();
        context.Articles.Add(a1);
        context.SaveChanges();
    }
    
    • 1
    • 2
    • 3
    • 4
    • 5
    • 6
    • 7
    • 8
    • 9
    • 10
    • 11
    • 12
    • 13
    • 14
    • 15
    • 16
    • 17
    • 18
    • 19
    • 20
    • 21
    • 22
    • 23
    • 24
    • 25
    • 26
    • 27

    假设我们想对已有的 Article 进行新增操作,我们也能利用导航属性来实现,举例如下:

    [TestMethod]
    public void TestAddComments()
    {
        using var context = new AppDbContext();
    
        var article = context.Articles.Single(a => a.Id == 20);
        article.Comments.Add(new Comment {CommentContent = "我觉得文章不怎么样" });
    
        context.SaveChanges();
    }
    
    • 1
    • 2
    • 3
    • 4
    • 5
    • 6
    • 7
    • 8
    • 9
    • 10

    查询中获取表关系

    刚才我们看到,Article 表和 Comment 表已经定义了主键和外键,在模型层面,定义了导航属性,并且定义了关系。此时我们试着查询出 Id == 20 的文章以及文章相应的 comment,我们先尝试下面的代码:

    [TestMethod]
    public void TestQueryArticles()
    {
        using var context = new AppDbContext();
    
        var article = context.Articles.Single(a=>a.Id==20);
        Console.WriteLine(article.ToString());
        article.Comments.ForEach(Console.WriteLine);
    }
    
    • 1
    • 2
    • 3
    • 4
    • 5
    • 6
    • 7
    • 8
    • 9

    我们发现,并没有关联到 comments 实体:

    请添加图片描述

    如果在查询的时候,需要关联数据,需要利用 Microsoft.EntityFrameworkCore 的扩展方法 Include() 方法:

    [TestMethod]
    public void TestQueryArticleAndComments()
    {
        using var context = new AppDbContext();
        var article = context.Articles.Include(a=>a.Comments).Single(a=>a.Id==20);
    
        // print article and related comments
        Console.WriteLine(article.ToString());
        article.Comments.ForEach(Console.WriteLine);
    }
    
    • 1
    • 2
    • 3
    • 4
    • 5
    • 6
    • 7
    • 8
    • 9
    • 10

    运行的测试结果如下,能够获取到 article 的 comments:

    请添加图片描述

  • 相关阅读:
    Vue3 reactive和ref详解
    vscode保存格式化自动去掉分号、逗号、双引号
    Doris数据库使用记录
    获取Windows远程桌面端口
    精品SpringCloud的高校招生信息管理系统-微服务分布式
    (详细图解过程) IDEA在创建类的的时候自动生成作者信息、时间等信息
    看我简单教会你如何按关键字搜索淘宝商品
    什么是Ajax?全面了解
    【JUC】一文弄懂@Async的使用与原理
    iOS开发Swift-10-位置授权, cocoapods,API,天气获取,城市获取-和风天气App首页代码
  • 原文地址:https://blog.csdn.net/stone0823/article/details/130907926