我正在使用实体框架来填充网格控件。有时当我进行更新时,我得到以下错误:

存储更新、插入或删除语句影响了意外的行数(0)。实体可能在加载实体后已被修改或删除。刷新ObjectStateManager条目。

我不知道怎么复制这个。但这可能和我更新的时间间隔有关系。有人见过这个吗,或者有人知道错误消息指的是什么吗?

编辑:不幸的是,我不再有自由重现我在这里遇到的问题,因为我离开了这个项目,不记得我最终是否找到了解决方案,是否有其他开发人员修复了它,或者是否我绕过了它。因此我不能接受任何回答。


当前回答

在我们的例子中,这个错误是由于将实体标记为已修改,而它们的属性并没有“真正”改变。例如,当你将相同的值赋给一个属性时,上下文可能会将其视为更新,而数据库则不会。

基本上,我们运行了一个脚本,用来自其他属性的连接值重新填充一个属性。对于很多记录来说,这意味着没有变化,但它将它们标记为修改。DB返回不同数量的更新对象,这可能触发了该异常。

我们通过检查属性值并仅在不同的情况下分配新的值来解决这个问题。

其他回答

我还遇到了这个错误。问题原来是由我试图保存到的桌子上的触发器引起的。触发器使用了'INSTEAD OF INSERT',这意味着0行被插入到该表,因此出现了错误。幸运的是,在可能的情况下,触发器功能是不正确的,但我猜它可能是一个有效的操作,应该以某种方式在代码中处理。希望有一天这能帮助到别人。

我也有这个错误。在某些情况下,实体可能不知道您正在使用的实际数据库上下文,或者模型可能不同。为此,设置:EntityState.Modified;EntityState.Added;

这样做:

if (ModelState.IsValid)
{
context.Entry(yourModelReference).State = EntityState.Added;
context.SaveChanges();
}

这将确保实体知道你正在使用或添加正在使用的状态。此时,需要设置所有正确的模型值。小心不要丢失任何可能在后台所做的更改。

希望这能有所帮助。

我也面临着同样可怕的错误……:)然后我意识到我忘记设置一个

@Html。HiddenFor(model => model. userprofile . userid)

用于更新对象的主键!我容易忘记这个简单但非常重要的事情!

顺便说一下:HiddenFor是ASP的。净MVC。

这是乐观并发特性的副作用。

不是100%确定如何在实体框架中打开/关闭它,但基本上它告诉你的是,当你从数据库中获取数据时,当你保存你的更改时,其他人已经更改了数据(这意味着当你保存它时,0行实际上得到了更新)。在SQL术语中,它们的更新查询的where子句包含行中每个字段的原始值,如果0行受到影响,它就知道出错了。

它背后的思想是,你最终不会覆盖你的应用程序不知道发生了什么变化——它基本上是。net在所有更新中附带的一个小安全措施。

如果它是一致的,那么它很可能发生在您自己的逻辑中(例如:您实际上是在选择和更新之间的另一个方法中自己更新数据),但它可能只是两个应用程序之间的竞争条件。

当附加一个数据库中不存在的对象时,我得到了这个异常。我假定对象是从单独的上下文中加载的,但如果这是用户第一次访问站点,则从头创建对象。我们有自动递增的主键,所以我可以替换

context.Users.Attach(orderer);

with

if (orderer.Id > 0) {
    context.Users.Attach(orderer);
}