ORM开发(2)-EF必杀神器

我们先从Code First模式出发,我们先创建三个类,来代表学生和课程的关系——Student,Course,Enrollment。有人可能会问,Enrollment是干嘛的?这是我们为了解耦所做的工作,如果我们单纯的让学生拥有多个课程,而一个课程有多个学生报名,那么就会形成多对多的关系,如果我们在其中添加一个中间层,那么则会形成多个一对一关系,从而完成解耦。

public class Student
    {
        public int ID { get; set; }
        public string LastName { get; set; }
        public string FirstMidName { get; set; }
        public DateTime EnrollmentDate { get; set; }

        public virtual ICollection<Enrollment> Enrollments { get; set; }
    }

    public enum Grade
    {
        A, B, C, D, F
    }

    public class Enrollment
    {
        public int EnrollmentID { get; set; }
        public int CourseID { get; set; }
        public int StudentID { get; set; }
        public Grade? Grade { get; set; }

        public virtual Course Course { get; set; }
        public virtual Student Student { get; set; }
    }

    public class Course
    {
        [DatabaseGenerated(DatabaseGeneratedOption.None)]
        public int CourseID { get; set; }
        public string Title { get; set; }
        public int Credits { get; set; }

        public virtual ICollection<Enrollment> Enrollments { get; set; }
    }

之后,我们创建一个继承自DbContext的类,这个类主要承担起和数据库的交互:

public class SchoolContext:DbContext
    {
        public SchoolContext() : base("SchoolContext")
        {
        }

        public DbSet<Student> Students { get; set; }
        public DbSet<Enrollment> Enrollments { get; set; }
        public DbSet<Course> Courses { get; set; }

        protected override void OnModelCreating(DbModelBuilder modelBuilder)
        {
            modelBuilder.Conventions.Remove<PluralizingTableNameConvention>();
        }
    }

OnModelCreating事件是在创建数据库中表时触发的,在方法中,我们只做了一件事,那就是让表的名字从复数变成单数。

虽然,我们启动时会在数据库中创建三个表,但是我们还没有数据,而且我们也没说连接哪个数据库。好吧,我们先写下连接字符串,前面已经说过了,这里贴一下就好了,EF自动调用它的:

<connectionStrings>
    <add name="SchoolContext" connectionString="data source=BLACKERXHUNTER\SQLEXPRESS;Initial Catalog=ContosoUniversity;Integrated Security=True;" providerName="System.Data.SqlClient" />
  </connectionStrings>

然后,我们再创建数据:

public class SchoolInitializer : System.Data.Entity.DropCreateDatabaseIfModelChanges<SchoolContext>
    {
        protected override void Seed(SchoolContext context)
        {
            var students = new List<Student>
            {
            new Student{FirstMidName="Carson",LastName="Alexander",EnrollmentDate=DateTime.Parse("2005-09-01")},
            new Student{FirstMidName="Meredith",LastName="Alonso",EnrollmentDate=DateTime.Parse("2002-09-01")},
            new Student{FirstMidName="Arturo",LastName="Anand",EnrollmentDate=DateTime.Parse("2003-09-01")},
            new Student{FirstMidName="Gytis",LastName="Barzdukas",EnrollmentDate=DateTime.Parse("2002-09-01")},
            new Student{FirstMidName="Yan",LastName="Li",EnrollmentDate=DateTime.Parse("2002-09-01")},
            new Student{FirstMidName="Peggy",LastName="Justice",EnrollmentDate=DateTime.Parse("2001-09-01")},
            new Student{FirstMidName="Laura",LastName="Norman",EnrollmentDate=DateTime.Parse("2003-09-01")},
            new Student{FirstMidName="Nino",LastName="Olivetto",EnrollmentDate=DateTime.Parse("2005-09-01")}
            };

            students.ForEach(s => context.Students.Add(s));
            context.SaveChanges();
            var courses = new List<Course>
            {
            new Course{CourseID=1050,Title="Chemistry",Credits=3,},
            new Course{CourseID=4022,Title="Microeconomics",Credits=3,},
            new Course{CourseID=4041,Title="Macroeconomics",Credits=3,},
            new Course{CourseID=1045,Title="Calculus",Credits=4,},
            new Course{CourseID=3141,Title="Trigonometry",Credits=4,},
            new Course{CourseID=2021,Title="Composition",Credits=3,},
            new Course{CourseID=2042,Title="Literature",Credits=4,}
            };
            courses.ForEach(s => context.Courses.Add(s));
            context.SaveChanges();
            var enrollments = new List<Enrollment>
            {
            new Enrollment{StudentID=1,CourseID=1050,Grade=Grade.A},
            new Enrollment{StudentID=1,CourseID=4022,Grade=Grade.C},
            new Enrollment{StudentID=1,CourseID=4041,Grade=Grade.B},
            new Enrollment{StudentID=2,CourseID=1045,Grade=Grade.B},
            new Enrollment{StudentID=2,CourseID=3141,Grade=Grade.F},
            new Enrollment{StudentID=2,CourseID=2021,Grade=Grade.F},
            new Enrollment{StudentID=3,CourseID=1050},
            new Enrollment{StudentID=4,CourseID=1050,},
            new Enrollment{StudentID=4,CourseID=4022,Grade=Grade.F},
            new Enrollment{StudentID=5,CourseID=4041,Grade=Grade.C},
            new Enrollment{StudentID=6,CourseID=1045},
            new Enrollment{StudentID=7,CourseID=3141,Grade=Grade.A},
            };
            enrollments.ForEach(s => context.Enrollments.Add(s));
            context.SaveChanges();
        }
    }

好吧,这个类稍稍有点长,不过其实结构挺简单的,我们创建了一个继承自DropCreateDatabaseIfModelChanges的泛型类,请把这个类的名字都出来——如果已经存在了一个同名的表在就重建一个表。嗯,就是这个意思。之后我们重载了seed方法,然后创建数据。对于每一个数据,我们调用了SchoolContext类里面的Set集合的Add方法,并保存,你可能会问我们为什么要些三遍SaveChanges,那是因为如果有哪个报错,就知道是哪里错了,它的使用也是超级简单的,只要在需要调用数据的地方添加这行代码即可:

private SchoolContext db = new SchoolContext();

之后随意改数据,删数据都不在话下~!

时间: 2024-08-10 00:05:36

ORM开发(2)-EF必杀神器的相关文章

ORM开发(1)-EF必杀神器

在这片战场上,如果真的存在能够一击必杀的武器,那么毫无疑问,那么它绝对就是传说中的Entity Framework了,它将ado.ent进行了更深层次的封装,使得数据库开发更加简单,但功能更加强大,它可以使用面向对象的方式来操作数据库中的所有数据. 在此之前我们先简单介绍一下三种常见的ORM模式: Code First Model First Database First 这三种模式各自有各自的运用特点,Code First适用于小型项目,先编程,用测试数据,把类都写好,然后生成数据库,这种方式

【iOS开发-13】大神器:如何利用cocoapods使用第三方类库,以针对UISwitch的第三方类库为例

上一篇笔记以及之前部分笔记里面有些属性设置了没效果,比如UISwitch开关控件的开关背景图片:或者直接没有那种我们想要的属性,比如直接用代码设置控件大小. 所以,我们需要用第三方类库,意思大概是我们不用UISwitch类来实例化一个对象了,而是用第三方的类来实例化一个对象,然后这个对象可以进行各种修改随心所欲. 当然,这里的逻辑就是,我们要导入第三方类库,可能需要把它头文件神马的引入进来,然后就可以实例化,但是如何用第三方类库?cocoapods神器. 安装和使用教程如下:点击这里(相当齐全)

ORM框架之一EF理解性

1.ORM概念 对象关系映射(英语:Object Relational Mapping,简称ORM,或O/RM,或O/R mapping),是一种程序技术,用于实现面向对象编程语言里不同类型系统的数据之间的转换.从效果上说,它其实是创建了一个可在编程语言里使用的“虚拟对象数据库”. 1.2,概念理解 O(Object) 它是程序设计中的对象,具体说来,也就是在开发过程中,所建立的Model层,在Model层中,每一个类都描述了一个对象,O就当理解为model层 R(Relational ) 它是

ORM框架中EF的作用和特点

存放于System.Linq.QueryAble 静态类中 并且所有的扩展方法扩展自 IqueryAble<TSource>泛型接口上 用途: 接收lambda表达式 利用EF生成对应的sql脚本   发送给ado.net   ado.net会发送给数据库执行

ORM开发(5)-日志和跟踪

为了使日志类更加灵活,我们自己写一个日志接口,自己实现它: public interface ILogger { void Information(string message); void Information(string fmt, params object[] vars); void Information(Exception exception, string fmt, params object[] vars); void Warning(string message); void

ORM开发(4)-分页与配置

我们接着给页面添加分页,在这里,官方范例给我们安利了一个PagedList.Mvc库,我们只需要在nuget包中就可以安装了. Install-package PagedList.Mvc 他的用法也挺简单的,首先引入命名空间: using PagedList; 然后再修改返回值: int pageSize = 3; int pageNumber = (page ?? 1); return View(students.ToList().ToPagedList(pageNumber, pageSiz

lucene开发序之luke神器

lucene是一款很优秀的全文检索的开源库,目前最新的版本是lucene4.4,关于lucene的历史背景以及发展状况,在这里笔者就不多介绍了,如果你真心想学习lucene,想必在这之前你已经对此作过一些了解. 有很多人知道lucene或者solr,但是却有很少人知道luke,在这里笔者就对luke做一个简单的介绍,Luke是一个用于Lucene搜索引擎的,方便开发和诊断的第三方工具,它可以访问现有Lucene的索引,并允许您显示和修改和调试.luke是google公司最早提供的,对于lucen

asp.net core3.1 实战开发(EF+Mysql 从数据库生成实体类到项目)

首先在程序包包管理器控制台 中执行以下语句安装依赖包Install-Package MySql.Data.EntityFrameworkCore -PreInstall-Package Pomelo.EntityFrameworkCore.MySqlInstall-Package Microsoft.EntityFrameworkCore.ToolsInstall-Package Microsoft.VisualStudio.Web.CodeGeneration.Design 在程序包包管理器控

asp.net core3.1 实战开发(EF+Sqlserver 从数据库生成实体类到项目)

首先程序包包管理器控制台安装以下包//Install-Package Microsoft.EntityFrameworkCore. Relationl Install-Package Microsoft.EntityFrameworkCoreInstall-Package Microsoft.EntityFrameworkCore.SqlServerInstall-Package Microsoft.EntityFrameworkCore.ToolsInstall-Package Microso