实体框架代码首先 1 到 1 数据添加
本文关键字:添加 数据 框架 代码 实体 | 更新日期: 2023-09-27 18:35:24
我正在使用代码优先的方式创建一个数据库。我有两个 1 对 1 关系的实体,但我真的不知道如何实例化它们。
假设这些是我的实体:
public class Foo
{
[Key]
public int Id {get;set;}
[ForeignKey("BigFoo")]
public int BigFooId {get;set;}
public virtual BigFoo BigFoo {get;set;}
}
public class BigFoo
{
[Key]
public int Id {get;set;}
[ForeignKey("Foo")]
public int FooId{get;set;}
public virtual Foo Foo {get;set;}
}
这是我的代码:
Foo foo = new Foo();
foo = db.Foo.Add(foo);
BigFoo big = new BigFoo {Foo = foo, FooId = foo.Id};
big = db.BigFoo.Add(big);
//HERE is my doubt
//I don't know if I have to add the relation also in the Foo object
//Do i need the following code?
//foo.BigFoo = big;
//foo.BigFooId = big.Id;
//db.Foo.Attach(foo);
//var entry = db.Entry(foo);
//entry.Property(x => x.BigFoo).IsModified = true;
db.SaveChanges();
该关系已经在我的 BigFoo 对象声明中设置,我是否需要在 Foo 对象中设置此关系,否则它将自动分配?
谢谢大家的帮助。
编辑:
我还有另一个疑问:我的外键名为 relatedentityIdField。
我还必须
用foo.BigFooId = big.Id;
还是这些关系是自动填充的?
添加示例-编辑
一个例子可以是关系 国家 - 总统
每个国家只有一位总统,每个总统只是一个国家的总统。
如何使用代码优先设置此关系?
对于当前的模型,您真正拥有的是两个一对多的单向关系。若要使用 Code First 创建一对一关系,还必须将依赖实体的 PK 定义为关系的 FK(有关详细说明,请查看此链接)。
public class Foo
{
public int Id{get;set;}
public virtual Boo Boo {get;set;}
}
public class Boo
{
[Key, ForeignKey("Foo")]
public int FooId{get;set;}
public virtual Foo Foo {get;set;}
}
使用此模型,可以按如下方式添加数据:
如果要创建新的
Foo
和Boo
,并且想要将它们关联起来,则可以执行以下操作:var boo=new Boo(); var foo=new Foo{Boo=boo }; context.Foos.Add(foo); context.SaveChanges();
您应该看到Boo
实体中的导航属性也已填充Foo
。
如果
Foo
已经存在,并且您想要创建一个与该 foo 相关的新Boo
:您可以在 foo 实体中设置
Boo
导航属性:var foo= context.Find(yourId); foo.Boo=new Boo(); context.SaveChanges();
或者,您可以只设置新
Boo
实体的 PK/FK 属性:var fooId=1;// You already have the Foo id var boo = new Boo() { FooId = fooId}; context.Boos.Add(boo); context.SaveChanges();
正如我之前所说,您的模型有两个不同的关系,因此您的导航属性并不真正相关。如果要证明这一点,请向实体添加两个集合:
public class Foo
{
[Key]
public int Id {get;set;}
[ForeignKey("BigFoo")]
public int? BigFooId {get;set;}
public virtual BigFoo BigFoo {get;set;}
public virtual ICollection<BigFoo> BigFoo{get;set;}// Add this property
}
public class BigFoo
{
[Key]
public int Id {get;set;}
[ForeignKey("Foo")]
public int? FooId { get; set; }
public virtual Foo Foo {get;set;}
public virtual ICollection<Foo> Foos{get;set;}// Add this property
}
稍后尝试:
using (var context=new MyContext())
{
var foo = new Foo();
context.Foos.Add(foo);
context.SaveChanges();
var boo = new BigFoo() { FooId = foo.Id};
context.Boos.Add(boo);
context.SaveChanges();
}
在最后一次SaveChanges
之后boo
您将Foo
实例中的导航属性BigFoos
并且foo
实例中的导航属性已正确填充。
注意:我将您的导航属性更改为 virtual
以满足延迟加载的要求之一,并且还将您的 FK 属性更改为可为空值以避免级联删除的循环。代码优先没有为可选关系设置级联删除。