为了账号安全,请及时绑定邮箱和手机立即绑定

实体框架.Remove()与.DeleteObject()

实体框架.Remove()与.DeleteObject()

12345678_0001 2019-07-25 16:53:20
实体框架.Remove()与.DeleteObject()您可以使用以下两种方法从EF中删除数据库中的项目。EntityCollection.Remove方法ObjectContext.DeleteObject方法第一个是EntityCollection第二个,第二个是ObjectContext。什么时候应该使用?一个优先于另一个吗?Remove()返回a bool并DeleteObject()返回void。
查看完整描述

2 回答

?
慕斯王

TA贡献1864条经验 获得超2个赞

使用这两种方法可以“ 从数据库中删除项目 ”通常不正确。确切地说,它是这样的:

  • ObjectContext.DeleteObject(entity)在上下文中标记实体Deleted。(它EntityStateDeleted后)。如果你打电话SaveChanges后EF发送SQL DELETE语句到数据库。如果违反了数据库中的引用约束,则将删除该实体,否则将引发异常。

  • EntityCollection.Remove(childEntity)标记父和childEntityas 之间的关系Deleted。如果childEntity从数据库中删除了自身,并且在调用时确实发生了什么,SaveChanges取决于两者之间的关系类型:

    • 如果关系是可选的,即从子级引用到数据库中的父级的外键允许NULL值,则此外部将被设置为null,如果调用SaveChangesNULL值,则将该值childEntity写入数据库(即两个被删除)。这发生在SQL UPDATE语句中。没有DELETE发表声明。

    • 如果需要关系(FK不允许NULL值)且关系未识别(这意味着外键不是子(复合)主键的一部分),则必须将子项添加到另一个父项或你必须明确删除孩子(DeleteObject当时)。如果您不执行任何这些操作,则会违反参照约束,EF会在您调用时抛出异常SaveChanges- 臭名昭着的“ 由于一个或多个外键属性不可为空而无法更改关系 ”异常或类似。

    • 如果关系正在识别(因为主键的任何部分都不可能是必需的NULL),EF也会标记childEntityDeletedas。如果调用SaveChangesSQL DELETE语句将被发送到数据库。如果未违反数据库中的其他引用约束,则将删除该实体,否则将引发异常。

我实际上您链接的MSDN页面上的 “ 备注”部分感到困惑,因为它说:“ 如果关系具有参照完整性约束,则在依赖对象上调用Remove方法会标记关系和依赖对象以进行删除。 ”。这对我来说似乎是不准确甚至是错误的,因为上面的所有三种情况都有“ 参照完整性约束 ”,但只有在最后一种情况下才会删除子。(除非它们与“ 依赖对象 ” 意味着一个参与识别关系的对象,但这可能是一个不寻常的术语。)


查看完整回答
反对 回复 2019-07-25
?
肥皂起泡泡

TA贡献1829条经验 获得超6个赞

如果你真的想使用Deleted,你必须使你的外键可以为空,但是你最终会得到孤立的记录(这是你不应该首先做的那个主要原因之一)。所以只需使用Remove()

ObjectContext.DeleteObject(entity)在上下文中将实体标记为已删除。(之后删除了EntityState。)如果之后调用SaveChanges,EF会向数据库发送SQL DELETE语句。如果违反了数据库中的引用约束,则将删除该实体,否则将引发异常。

EntityCollection.Remove(childEntity)将parent和childEntity之间的关系标记为已删除。如果从数据库中删除了childEntity本身,并且在调用SaveChanges时究竟发生了什么,取决于两者之间的关系类型:

值得注意的是,设置.State = EntityState.Deleted 不会触发自动检测到的更改。 档案


查看完整回答
反对 回复 2019-07-25
  • 2 回答
  • 0 关注
  • 655 浏览
慕课专栏
更多

添加回答

举报

0/150
提交
取消
意见反馈 帮助中心 APP下载
官方微信