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

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

您可以使用以下两种方法从EF中删除数据库中的项目。

第一个是EntityCollection第二个,第二个是ObjectContext

什么时候应该使用?

一个优先于另一个吗?

Remove()返回a boolDeleteObject()返回void


12345678_0001
浏览 656回答 2
2回答

慕斯王

使用这两种方法可以“ 从数据库中删除项目 ”通常不正确。确切地说,它是这样的:ObjectContext.DeleteObject(entity)在上下文中标记实体Deleted。(它EntityState是Deleted后)。如果你打电话SaveChanges后EF发送SQL DELETE语句到数据库。如果违反了数据库中的引用约束,则将删除该实体,否则将引发异常。EntityCollection.Remove(childEntity)标记父和childEntityas 之间的关系Deleted。如果childEntity从数据库中删除了自身,并且在调用时确实发生了什么,SaveChanges取决于两者之间的关系类型:如果关系是可选的,即从子级引用到数据库中的父级的外键允许NULL值,则此外部将被设置为null,如果调用SaveChanges此NULL值,则将该值childEntity写入数据库(即两个被删除)。这发生在SQL UPDATE语句中。没有DELETE发表声明。如果需要关系(FK不允许NULL值)且关系未识别(这意味着外键不是子(复合)主键的一部分),则必须将子项添加到另一个父项或你必须明确删除孩子(DeleteObject当时)。如果您不执行任何这些操作,则会违反参照约束,EF会在您调用时抛出异常SaveChanges- 臭名昭着的“ 由于一个或多个外键属性不可为空而无法更改关系 ”异常或类似。如果关系正在识别(因为主键的任何部分都不可能是必需的NULL),EF也会标记childEntity为Deletedas。如果调用SaveChangesSQL DELETE语句将被发送到数据库。如果未违反数据库中的其他引用约束,则将删除该实体,否则将引发异常。我实际上对您链接的MSDN页面上的 “ 备注”部分感到困惑,因为它说:“ 如果关系具有参照完整性约束,则在依赖对象上调用Remove方法会标记关系和依赖对象以进行删除。 ”。这对我来说似乎是不准确甚至是错误的,因为上面的所有三种情况都有“ 参照完整性约束 ”,但只有在最后一种情况下才会删除子。(除非它们与“ 依赖对象 ” 意味着一个参与识别关系的对象,但这可能是一个不寻常的术语。)

肥皂起泡泡

如果你真的想使用Deleted,你必须使你的外键可以为空,但是你最终会得到孤立的记录(这是你不应该首先做的那个主要原因之一)。所以只需使用Remove()ObjectContext.DeleteObject(entity)在上下文中将实体标记为已删除。(之后删除了EntityState。)如果之后调用SaveChanges,EF会向数据库发送SQL DELETE语句。如果违反了数据库中的引用约束,则将删除该实体,否则将引发异常。EntityCollection.Remove(childEntity)将parent和childEntity之间的关系标记为已删除。如果从数据库中删除了childEntity本身,并且在调用SaveChanges时究竟发生了什么,取决于两者之间的关系类型:值得注意的是,设置.State = EntityState.Deleted 不会触发自动检测到的更改。 (档案)
打开App,查看更多内容
随时随地看视频慕课网APP