【问题标题】:Entity Framework Collection was modified; enumeration operation may not execute修改了实体框架集合;枚举操作可能无法执行
【发布时间】:2012-03-13 10:44:17
【问题描述】:

我目前使用的是 EF 4.0。我的目标是删除一个子集合并将新集合添加到同一个父集合。

 public void AddKids(int parentId, Kids newKids)
 {
    using (ModelContainer context = new ModelContainer(connectionString))
    {
        using (TransactionScope scope = new TransactionScope())
        {
            var query = from Parent _parent in context.Parents
                        where _parent.ParentId == parentId select _parent;

            Parent parent = query.Single();
            while (parent.Kids.Any())
            {
                context.Kids.DeleteObject(parent.Kids.First());
            }

            if (newKids != null)
            {
                foreach (Kid _kid in newKids)
                {
                    parent.Kids.Add(new Kid
                    {
                        Age = _kid.Age,
                        Height = _kid.Height
                    });
                }
            }
            scope.Complete();
        }
        context.SaveChanges(); //Error happens here
    }
}

错误来自标题:集合已修改;枚举操作可能无法执行。

任何帮助将不胜感激。

【问题讨论】:

  • @JustinNiessner:谢谢,我编辑了我的问题。
  • 现在我也想知道 parent 是在哪里定义的。
  • 你打开了一个新的上下文但是你修改了一个旧的缓存?父实例。我怀疑有你的问题。您应该打开上下文,检索父级并对其进行修改。
  • 我再次编辑了我的问题。谢谢你们。
  • 我尝试设置一个完整的模拟副本。它对我来说很好:/.

标签: c# entity-framework


【解决方案1】:

您看到这一点是因为您从当前具有活动操作的集合中删除了对象。更具体地说,您正在更新 Kids 集合,然后在 while 循环中对其执行 Any() 运算符。使用 IEnumerable 实例时,这不是受支持的操作。我可以建议您将您的 while 改写为:

parent.Kids.ToList().ForEach(r => context.Kids.DeleteObject(r));

希望对你有帮助。

【讨论】:

  • 我也试过你的方法,但同样的错误。经过几个小时的挖掘,结果证明发布的代码工作正常。在此过程的稍后部分,我发现了修改“Kids”集合的问题。感谢您的帮助。
  • 我很高兴能帮上忙。祝你的项目好运。
  • 完美!也帮助了我:D
  • 也许值得一提的是,当您将实体保存在 IEnumerable 中时,EF (afaik) 会延迟加载实体,并从您实际上并未从数据库将您带入一个,怎么说呢,时间悖论ToList 强制拉动立即发生(急切地加载?)。现在你有真正的实体可以推动。 ;^)
  • 我在使用 EF ~6 时遇到了同样的错误。我有两个具有完全相同属性和数据类型的实体。我正在使用任务,这意味着这两个实体的删除是同时发生的。两个实体之一遇到此错误,而另一个则没有。现在,如果我同步触发删除,我不会收到错误消息。也许有人可以阐明?
【解决方案2】:

我遇到了同样的问题/错误。 ruffin的解决方案奏效了。

这会崩溃:

var objectsToRemove = employee.Contracts.Where(m => ...);
objectsToRemove.ForEach(m => _context.Contracts.Remove(m));

这对我有用:

var objectsToRemove = employee.Contracts.Where(m => ...).ToList();
objectsToRemove.ForEach(m => _context.Contracts.Remove(m));

【讨论】:

  • 这里不需要确认答案。如果他们对你有帮助,请点赞,无需重复。
猜你喜欢
  • 1970-01-01
  • 1970-01-01
  • 2012-04-13
  • 1970-01-01
  • 1970-01-01
  • 2015-06-17
  • 2020-02-07
相关资源
最近更新 更多