在使用Npgsql框架连接到PostgreSQL数据库的C#WinForms项目中,我需要允许用户在DGV中的任何位置进行更改,然后单击按钮,我需要启动一个过程来查找那些更改并将其提交。到数据库。
我目前有下面的代码遍历DGV的DataTable,在每个DataRow中,它遍历每一列,并将DataRowVersion的原始值与建议值进行比较:
private void CheckDgvForChangedCells(DataTable dt)
{
string strOriginalValue;
string strEnteredValue;
int intRowIndex;
int intColumnIndex;
for (intRowIndex = 0; intRowIndex <= dt.Rows.Count - 1; intRowIndex++)
{
for (intColumnIndex = 0; intColumnIndex <= dt.Columns.Count - 1; intColumnIndex++)
{
DataRow drCurrRow = dt.Rows[intRowIndex];
strOriginalValue = drCurrRow[intColumnIndex, DataRowVersion.Original].ToString();
strEnteredValue = drCurrRow[intColumnIndex, DataRowVersion.Proposed].ToString();
if (strOriginalValue != strEnteredValue)
{
// Do something
}
}
}
}
填充DataTable的数据库表当前只有1400多行,随着时间的增长,将增加7列,而当我将它们放在一起时,我想知道这是否是查找所有已更改内容的最佳/最有效方法值并在找到每个数据库时更新数据库。
[更新]
[Per Steve在我尝试使用DataTable.GetChanges()
的注释中的建议,但我没有看到如何仅获取给定行中已更改的列。
我更改了三行中的各个单元格,并且dtChanges.Rows.Count
为3,正如预期的那样,但整个行都在其中,新值已在编辑的单元格中。我没有看到如何使用dtChanges
仅使用已更改的行的相应已更改的列来更新数据库。
private void CheckDgvForChangedCells(DataTable dt)
{
DataTable dtChanges = dt.GetChanges();
foreach (DataRow row in dtChanges.Row)
{
switch(row.RowState)
{
case DataRowState.Modified:
// TODO
ExecuteUpdateCommand(row);
break;
case DataRowState.Added:
// TODO
ExecuteInsertCommand(row);
break;
case DataRowState.Deleted:
// This is trickier. You cannot access any field in a deleted row
// So you first need to call row.RejectChanges, get the primary key value
// delete the row on the database, re-delete the row in the DataTable
// TODO
ExecuteDeleteCommand(row);
break;
}
}
// Do not forget to call AcceptChanges to set the table to a pristine initial editing state
dt.AcceptChanges();
}
}