您的位置:首页 > 其它

MVC3+EF4.1学习系列(四)----- ORM关系的处理

2016-08-26 10:34 288 查看

文章索引和简介

上篇文章 终于把基础的一些操作写完了 但是这些都是单表的处理 而EF做为一个ORM框架 就必须点说说对于关系的处理

处理好关系 才能灵活的运用EF

关于关系的处理 一般就是 一对一 一对多 多对多 还有就是采用双向关联还是单项关联 而关系的处理 站长dudu的文章 就已经有了很好的介绍

推荐大家去看下 -------dudu的实体关系总结 这样大家对实体关系也就有了初步的认识了 但是在dudu的文章里 一直没有说如何处理多对多时 关系表

里有其他数据时怎么办(这个问题曾经困扰了我好久~~ 见人就问) 这里写下当时得到的几种方案 也希望能跟大家探讨下 好了 从实际项目开始 继续完善我们

的demo 并在从中探讨关系

先把原文中的完成后的图贴上来 也就是我们要处理的关系

修改登记表



using System; using System.Collections.Generic; using System.ComponentModel.DataAnnotations;
namespace ContosoUniversity.Models {     public class Enrollment     {         public int EnrollmentID { get; set; }
public int CourseID { get; set; }
public int StudentID { get; set; }
[DisplayFormat(DataFormatString="{0:#.#}",ApplyFormatInEditMode=true,NullDisplayText="No grade")]         public decimal? Grade { get; set; }
public virtual Course Course { get; set; }         public virtual Student Student { get; set; }     } }




七.多对多关系的思考与讨论

项目的类和关系建完了 这里我最想和大家探讨与分享的就是 这个如何处理多对多的关系

看我们的例子 其实有两个多对多 一个是课程和教师 还有一个是学生和选课

课程与教师 我们是直接使用多对多 没有为关系表建立实体类 因为我们的关系表不需要存储其他数据

而在学生和选课这里 要存储成绩 关系表里要存储其他的东西 这时 我们为关系表也建立了实体类 关系变成里 学生 1对多 关系表 课程也是1对多关系表

也就是说 当遇到使用多对多时 关系表还需要存储其他东西时(本文是成绩) 可以把多对多拆穿 两个1对多 还有 实际项目不建议使用多对多来处理关系

这是这个项目给的启事 请问大家是如何解决这种情况的呢? 所有的ORM都会遇到这种问题的吧?

这里 感谢下 桀骜的灵魂dax.net

他们在领域驱动群里 给了我另一种解答 直接上图



晴天 15:23:04 分数之间不需要区分个体,所以是值对象 晴天 15:23:23 学生和课程是需要系统维护的,所以是聚合根

晴天 15:25:13 CourseMark保存针对Course的引用 晴天 15:25:28 Student下包含多个CourseMark

dax.net 关于双向关联

是不是双向关联不重要,首先要确定聚合根

班级是聚合根,学生也是聚合根 如果你的应用程序只是维护班级的基本信息,而不需要读取这个班级到底有哪些学生,那么就不需要往班级的聚合里添加学生

相反,通常情况下,学生的一个属性是班级,所以学生聚合里可以将班级加进去

八.关于EF的关系映射

看了这么多各种关系的类 他们之间存才的关系 多对多 一对一 一对多 处理这些映射是很麻烦的事

我们有三种方法 1.按EF默认的规则 自动生成 但是有时生成的不是我们想要的

2.通过特性的定义 来配置如何映射关系 以及如何映射到数据库 这篇文章提到了一些

3.通过流利的API 方式来定义 这也是我推荐的方式

看这篇文章的例子



using System; using System.Collections.Generic; using System.Data.Entity; using ContosoUniversity.Models; using System.Data.Entity.ModelConfiguration.Conventions;
namespace ContosoUniversity.Models {     public class SchoolContext : DbContext     {         public DbSet<Course> Courses { get; set; }         public DbSet<Department> Departments { get; set; }         public DbSet<Enrollment> Enrollments { get; set; }         public DbSet<Instructor> Instructors { get; set; }         public DbSet<Student> Students { get; set; }         public DbSet<OfficeAssignment> OfficeAssignments { get; set; }
protected override void OnModelCreating(DbModelBuilder modelBuilder)         {             modelBuilder.Conventions.Remove<PluralizingTableNameConvention>();             modelBuilder.Entity<Instructor>()                 .HasOptional(p => p.OfficeAssignment).WithRequired(p => p.Instructor);             modelBuilder.Entity<Course>()                 .HasMany(c => c.Instructors).WithMany(i => i.Courses)                 .Map(t => t.MapLeftKey("CourseID")                     .MapRightKey("InstructorID")                     .ToTable("CourseInstructor"));             modelBuilder.Entity<Department>()                 .HasOptional(x => x.Administrator);         }     } }




依然很痛苦啊 这要多勇敢 才能把编写model 到再编写数据库映射等 写完 还有这么多api要记什么意思 实在是太痛苦了

不要怕 想用code fisrt 有干净的poco 但又不想写这些的 你们的福音来了 强烈推荐使用

Entity Framework Power Tools

可以根据数据库 一键生成想要的model 与映射 原子中也有介绍的了 介绍连接

生成后 和我们自己写的一样 而且更加规范 统一的映射管理 真的很完美~~

九.总结

通过这节 终于把ORM的关系理顺了 但是 这只是把关系建立起来 关系的处理远没结束

下一节 查找关联数据 如何利用好延迟加载与懒惰加载
内容来自用户分享和网络整理,不保证内容的准确性,如有侵权内容,可联系管理员处理 点击这里给我发消息
标签: