3

我需要使用实体框架 4.1(POCO)单击一次按钮更新 100 条记录。我需要将修改后的记录保存在数据库中而不进行数据库往返(以避免性能问题)。

我已经看到了一些分离和附加的解决方案。

附加时出现错误 IEntityChangeTracker 的多个实例无法引用实体对象

所以先尝试分离,得到新的错误 The object cannot be detached because it is not attach to the ObjectStateManager

我正在使用存储库模式来获取实体列表并传递给 UI 层以在网格中进行绑定。

在按钮单击中,我将这些实体传回 DB 层以进行更新。

它工作正常,选择实体并执行 context.applychanges。由于性能问题,我需要避免这种往返。

    public void Update(OPRPortCall portCall)
    {
        using (VMEntities context = new VMEntities())
        {
            context.Detach(portCall); //The object cannot be detached because it is not attached to the ObjectStateManager.
            context.AttachTo("OPRPortCalls", portCall); //An entity object cannot be referenced by multiple instances of IEntityChangeTracker
            context.ObjectStateManager.ChangeObjectState(portCall, EntityState.Modified);

            context.SaveChanges();
        }
    }

建议我对此的任何解决方案。

克里斯托弗

4

2 回答 2

1

从技术上讲,您可以通过首先测试对象是否已附加来解决此问题:

public void Update(OPRPortCall portCall)
{
    using (VMEntities context = new VMEntities())
    {
        ObjectStateEntry ose;
        this.ObjectStateManager.TryGetObjectStateEntry(portCall, out ose);
        if (ose == null)
        {
            context.OPRPortCalls.Attach(portCall);
        }
        context.ObjectStateManager.ChangeObjectState(portCall, EntityState.Modified);

        context.SaveChanges();
    }
}
于 2013-02-21T13:29:42.250 回答
0

您可以仅分离从上下文中检索到的实体,在您的示例中创建上下文(此时没有实体),然后尝试分离。

对于第二个问题,我认为您有另一个已附加实体的上下文,因此您不能将实体附加到第二个上下文。

对于这个问题(附加/分离),避免创建多个上下文并只使用一个上下文(也许您可以将它作为函数的参数传递或将其设置为私有类变量)。

对于更新 100 个实体的具体问题,您可以: 1. 如果您可以为所有实体更新同一列(将值传递给它并执行 UPDATE 语句),则创建一个存储过程 2. 更新所有实体,然后调用 SubmitChages()此命令 EF 执行 UPDATE TABLE 100 次 3. 对数据库执行自定义查询命令,例如“UPDATE TABLE SET ...”

我希望这会有所帮助。

于 2013-02-21T11:31:40.293 回答