DataTable:在插入新的数据行之前删除旧的数据行是否安全?

3
在一个类型化的 DataSet 中,我有一个多对多关系表。为了便于更新,在添加新关系之前,我会删除旧的关系(可能与以前相同)。现在我想知道这种方法是否是安全的,或者我应该确保只删除那些真正被删除的(例如使用 LINQ),并且仅添加那些真正新增的。
在 SQL Server 中,关系表定义了唯一约束条件,两个外键组合成主键。
DataAdapter 更新 DataRow 的顺序(RowState 不等于 Unchanged)是否是可预测的?换句话说,当关键字已经存在时,DataAdapter.Update(DataTable) 是否会导致异常?
这是数据模型: Datamodel 以下是代码的一部分(LbSymptomCodes 是 ASP.Net ListBox):
Dim daTrelRmaSymptomCode As New ERPModel.dsRMATableAdapters.trelRMA_SymptomCodeTableAdapter
For Each oldTrelRmaSymptomCodeRow As ERPModel.dsRMA.trelRMA_SymptomCodeRow In thisRMA.GettrelRMA_SymptomCodeRows
    oldTrelRmaSymptomCodeRow.Delete()
Next
For Each item As ListItem In LbSymptomCodes.Items
    If item.Selected Then
        Dim newTrelRmaSymptomCodeRow As ERPModel.dsRMA.trelRMA_SymptomCodeRow = Services.dsRMA.trelRMA_SymptomCode.NewtrelRMA_SymptomCodeRow
        newTrelRmaSymptomCodeRow.fiRMA = Services.IdRma
        newTrelRmaSymptomCodeRow.fiSymptomCode = CInt(item.Value)
        Services.dsRMA.trelRMA_SymptomCode.AddtrelRMA_SymptomCodeRow(newTrelRmaSymptomCodeRow)
    End If
Next
daTrelRmaSymptomCode.Update(Services.dsRMA.trelRMA_SymptomCode)

提前感谢您。

2个回答

2
我认为ADO.NET中的DataAdapter足够聪明,能够按正确顺序执行删除/插入操作。
然而,如果你真的想确保更新以正确的顺序进行,你应该手动使用Select方法为每个特定的行状态返回一个数据行数组。然后,你可以在数据行数组上调用Update方法。
DataTable tbl = ds.Tables["YourTable"];

// Process any Deleted rows first
adapter.Update(tbl.Select(null, null, DataViewRowState.Deleted));

// Process any Updated/Modified rows
adapter.Update(tbl.Select(null, null, DataViewRowState.ModifiedCurrent));

// Process the Inserts last
adapter.Update(tbl.Select(null, null, DataViewRowState.Added));

谢谢。但这将导致三个数据库调用(和三个事务),而不是一个。当已接受的更改中添加的行更新失败时,我无法拒绝对已删除和更改行进行的更改。 - Tim Schmelter
@TimSchmelter:你能否将所有更新操作放在一个try/catch块中,以便在出现任何错误时回滚? - codingbadger
可能性是存在的,但会比较困难,因为在类型化数据集中,这种逻辑被封装在自动生成的 TableAdapters 中。我必须在一个单独的文件中扩展这些适配器的部分类,并公开 DataAdapter 本身以提供事务。但我很想避免这种额外的努力 ;) - Tim Schmelter
谢谢,我喜欢这个解决方案。 - Athit Upakan

1

关于DA我不确定,但理论上DB事务应按以下顺序执行:删除、插入、更新。

从msdn的资料来看,更新方法的确切措辞是:

尝试将DataTable中的所有更改保存到数据库中。(包括从表中删除任何行,添加插入到表中的行以及更新表中已更改的任何行。)

关于您删除项目并可能重新插入相同项目的解决方案,通常情况下应避免这样做,因为它会对DB产生负载。在高容量应用程序中,您希望尽可能减少对DB的调用,因为它们非常昂贵;计算时间,从确定哪些行更新是虚假的方面来看,是便宜的。


谢谢。由于用户(而且根本没有多少用户)只能在ListBox中选择1-5个项目,因此对数据库的额外负载相当有限。 - Tim Schmelter

网页内容由stack overflow 提供, 点击上面的
可以查看英文原文,
原文链接