【问题标题】:EF4 c# updating nested object in 1:nEF4 c# 在 1:n 中更新嵌套对象
【发布时间】:2013-09-24 14:25:54
【问题描述】:

我有一个嵌套的 EF 对象挂在其父对象上。 1:n关系

[父]-[n..child]

嵌套对象子对象是动态的,将通过 GUI 更新。

我在数据库上更新它时遇到问题。

错误信息: ObjectStateManager 中已存在具有相同键的对象。 ObjectStateManager 无法跟踪具有相同键的多个对象。

这是第二版的问题。我对判断 preExist 的 if 块进行了更正

提前感谢您的帮助

坐鸭

主要更新

void MainUpdate
{
    var context = new FamilyEntities();
    parent = getParentFromGui();
    parent.UpdateRelatedEntities(context);
    context.dispose();

}

对象父对象已在 Gui 中更新

parent getParentFromGui()
{
    parent myParent = parentBindingSource.DataSource as parent;
    foreach(child c in childrenBindingSource)
    {
        myParent.children.Add(c);
    }
    return myParent
}

修改 UpdateRelatedEntities

public static void UpdateRelatedEntities(this parent entity, FamilyEntities context)
    {
        if (entity == null) return;


        var res = context.parent.Where(x => x.uid_parent == entity.uid_parent);
        var rec = res.FirstOrDefault();

        context.parent.Attach(rec);
        context.parent.ApplyCurrentValues(entity);                                 

        foreach (var c in entity.children)
        {
            bool preExist = context.children.FirstOrDefault(x => x.child_uid == c.child_uid);
            if (preExist != null)
            {                
                context.children.Attach(obj);
                context.children.ApplyCurrentValues(c);
            }
            else
            {                    
                // This Part throw ERROR 
                context.children.AddObject(c);
            }
        }            

        context.SaveChanges();
    }

我做错了什么?

发送很多!

【问题讨论】:

  • context.shaft_section 是什么?这是否保证孩子不在 children 集合中?
  • ups 抱歉,应该是儿童版。感谢指正
  • 现在您正在检查一个集合是否等于集合中的一个项目。这应该总是错误的。像 context.children.Any(x => x.child_uid == c.child_uid) 这样的东西应该可以工作

标签: c# entity-framework entity-framework-4


【解决方案1】:

试试这个语法

foreach (var c in entity.children)
{
    var preexistingChildren = context.children.FirstOrDefault(x => x.child_uid == c.child_uid)
    if (preexistingChildren != null)
    {
        context.children.Attach(obj);
        context.children.ApplyCurrentValues(c);
    }
    else
    {                    
        // ERROR
        context.children.AddObject(c);
    }
}  

【讨论】:

  • 谢谢,但它不起作用,entites(空表)中没有现有的 obect c,但它一直抛出错误消息
【解决方案2】:

目前尚不清楚 *context.shaft_section* 是什么,但从逻辑上讲,您的代码存在问题:您实际上并没有检查 context.children 中是否存在元素,您的 isExist 来自一些其他检查。

这很容易出现像您遇到的错误。

修改后

现在您只是将集合与元素进行比较: context.children.Equals(c) 总是假的

第二次编辑后 这一行:

context.parent.Attach(rec);

将对象或对象图(意思是所有的孩子)附加到上下文中(参见MSDN)。 因此,当您尝试这样做时,您所有的孩子都已经属于上下文

context.children.AddObject(c);

因此出现错误 - 您尝试添加相同的对象两次。

【讨论】:

  • 哦!我的评论来不及了
  • 不,它不起作用,问题是我无法添加对象 context.children.AddObject(c);
  • 等一下。 父实体来自哪里,数据库?如果是这样,很可能它是现有的孩子,已经包含在 context 中。如果 c in entites 实际上是 DB 中的一个空表,还需要检查一件事 - 确保关系实际上是有效的,并且单亲不会突然映射到该子表中的所有行
  • 我已经根据您的帖子编辑编辑了我的答案。这一行: context.parent.Attach(rec);将对象或对象图(意思是 - 所有的孩子)附加到上下文
  • 是的,父母来自数据库。一开始父母没有孩子。 GUI会添加一些。更新将实现子表。感谢您的解释,现在对我有意义。你能解释一下你的最后一句话吗?应该如何更新我的子表?
猜你喜欢
  • 2012-05-28
  • 2023-01-22
  • 2019-11-03
  • 1970-01-01
  • 2018-06-03
  • 2014-07-13
  • 2019-11-02
  • 2016-02-20
  • 2021-12-15
相关资源
最近更新 更多