EF
类对象创建
[Table("表名")]
public class Person
{
// EF 默认制定 Id 为主键, 可以使用 [Key] 指定
// 使用 Column("Name") 指定表属性
public int Id { get; set; }
public string Name { get; set; }
// 可空字段
public int? Age { get; set; }
// [DatabaseGenerated] 使用数据库的默认值(如果有的话)
}
连接上下文
Public class MyDbContext : DbContext
{
public DbSet<Person> Persons { get; set; }
Public MyDbContext() : base("name=ConnectionName which is at the web.config")
{
}
}
使用
using (MyDbContext ctx = new MyDbContext()) {
Person p = new Person();
p.Name = "Jack";
ctx.Persons.Add(p)
ctx.SaveChanges();
}
Fluent API
- 创建一个 POCO 类
- 创建一个继承 EntityTypeConfiguration<> 的类(用于做 POCO 到表的映射)
- 构造方法中先使用 ToTable("table name") 指明表明
- 在构造方法中后继写对表中字段的约束
- Property(p => P.name).HasMaxLength(100);
- Property(p => P.name).IsRequired();
- Property(p => P.name).IsOptional();
- HasColumnName("Name") 在数据库中的名字
- IsUnicode(true)
- IsFixedLength(100)
- HashKey(p => p.Id)
- this.Ignore(p => p.Name) 忽略 Name 的映射(不映射到数据库)
- 创建一个继承 DbContext 的类(用于维护连接)
- 重写 OnModelCreating(ModelBuilder modelBuilder) modelBuilder 可以实现大量 EF 的配置
- 将要操作的数据表对应的 POCO 声明为属性, 类型为 DbSet<POCO>
- 构造方法 Name : base("name=xxx")
- 在 OnModelCreating 方法中使用 modelBuilder 进行配置
- modelBuilder.Configurations.AddFromAssembly(Assembly.GetExecutingAssembly()) // 读取当前程序集中所以继承 EntityTypeConfiguration 的类,但是 .NET Core 不支持
- 当然也可以通过 modelBuilder.Entity<类型>().ToTable("Name"), 将 POCO 读取到 modelBuilder 中, 这样也不需要有`类型`继承EntityTypeConfiguration
关系对应
Config 对象
- Aconfig.HasXxx(b => b.Id).WithXxx();
- Xxx 为 Required, Optional, Many
实例 一对多
class Class
{
// 注意: id 这些自增的要为 long 类型
public long Id { get; set; };
public string Name { get; set; };
}
class Student
{
public long Id { get; set; };
public string Name { get; set; };
// 加上两行(EF 默认配置要求有ClassId), 如果想要修改外间的名字, 需要在 StudentConfig 中配置 HasRequired(e => e.Class).WithMany().HasForeignKey(e => e.Class_Id) 其中 Class_Id 是自定义的属性
public long ClassId { get; set; };
public virtual Class Class { get; set; };
}
多对多
如果指向一个列表, 应该使用 virtual ICollection<类型> 名称 { set; get; }, 在多对多中两个 POCO 都要有互相的 Icollection
class Teacher
{
public long Id { get; set; }
public string Name { get; set; }
public virtual ICollection<Student> Students { get; set; }
}
class Student
{
public long Id { get; set; };
public string Name { get; set; };
public virtual ICollection<Teacher> Teachers { get; set; }
}
可以选择在 StudentConfig 的构造方法中
HasMany(e => e.Teachers)
.WithMany(e => e.Students)
.Map(e => e.ToTable("TeacherStudentRelations")
.MapLeftKey("TeacherId")
.MapRightKey("StudentId"))
EF 的五个状态
- Unchanged
- Detached
- Added
- Removed
- Modified
每次使用 ctx.SaveChanges() 等操作就是修改状态的操作; 如果我们查询仅仅是为了显示数据, 可以使用.AsNoTracking()返回的IQuerySet, 集合的状态是`ctx.Entry(p).State = Detached`, 对数据的修改都是无效的