数据适配器可以与数据表一起工作。因此,我实际上已经将我的组合成一个类并且工作得很好。除了我的东西的复杂性之外,这里有一个片段可能会帮助你。添加参数时,您可以从 DataTable 中识别数据来自的列源。这样,当一条记录在内部被标识为“已添加”或“已更新”(或“已删除”)时,当您构建 SQL 插入/更新/删除命令时,它将从相应行的列中提取数据。
例如。假设我有一个 DataTable,主键是“MyID”并且有列“ColX, ColY, ColZ”。我创建了我的 DataAdapter 并构建了我的选择、更新、删除命令,例如......(?是参数的占位符)
DataAdapter myAdapter = new DataAdapter()
myAdapter.SelectCommand = new OleDbCommand();
myAdapter.InsertCommand = new OleDbCommand();
myAdapter.UpdateCommand = new OleDbCommand();
myAdapter.DeleteCommand = new OleDbCommand();
myAdapter.SelectCommand.CommandText = "select * from MyTable where MyID = ?";
myAdapter.InsertCommand.CommandText = "insert into MyTable ( ColX, ColY, ColZ ) values ( ?, ?, ? )";
myAdapter.UpdateCommand.CommandText = "update MyTable set ColX = ?, ColY = ?, ColZ = ? where MyID = ?";
myAdapter.DeleteCommand.CommandText = "delete from MyTable where MyID = ?";
现在,每个人都必须有各自的“参数”。参数必须以与其对应的“?”相同的顺序添加。占位符。
// 虽然我在准备参数时输入了虚假值,但它只是为了 // 数据类型的目的。应用更改时,它确实会通过数据适配器进行更改
OleDbParameter oParm = new OleDbParameter( "myID", -1 );
oParm.DbType = DbType.Int32;
oParm.SourceColumn = "myID"; // <- this is where it looks back to source table's column
oParm.ParameterName = "myID"; // just for consistency / readability reference
myAdapter.SelectCommand.Parameters.Add( oParm );
根据参数类型对其余参数执行类似操作... char、int、double 等
再一次,我喜欢一个包装类,它在每个表的基础上处理管理......简而言之
public myClassWrapper
{
protected DataTable myTable;
protected DataAdapter myAdapter;
... more ...
protected void SaveChanges()
{
}
}
它比这更复杂,但在“SaveChanges”期间,数据表和 dataAdapter 出于各自的目的而同步。现在,刷新数据。我检查表的状态,然后您可以将整个表传递给 dataAdapter 进行更新,它将循环遍历所有更改的记录并推送相应的更改。但是,您必须捕获任何可能的数据错误。
myAdapter.Update( this.MyTable );
当它找到每个“更改”的记录时,它从列源中提取值,这些值由在传递给适配器的表中找到的参数标识,以进行处理。
希望这使您对遇到的问题有了很大的了解。
---- 每个反馈的评论 ----
我会将您的更新放在 try/catch 中,然后进入程序以查看异常是什么。错误的消息和/或内部异常可能会提供更多信息。但是,请尝试简化您的 UPDATE 以仅包含带有 WHERE “Key”元素的几个字段。
此外,我从第一部分答案中错过了这一点。您可能必须识别数据表的“PrimaryKey”列。为此,它是 DataTable 的一个属性,它需要表示表的主键的列数组。我所做的是...
// set the primary key column of the table
DataColumn[] oCols = { myDataTbl.Columns["myID"] };
myDataTbl.PrimaryKey = oCols;
我会为您的 UPDATE 注释掉您的完整更新字符串及其所有参数。然后,使用我的示例(仅设置 2-3 列和 where 子句)简单地构建它
myAdapter.UpdateCommand.CommandText = "update MyTable set ColX = ?, ColY = ? where MyID=?";
Add Parameter object for "X"
Add Parameter object for "Y"
Add Parameter object for "MyID"
选择像 int 或 char 这样的字段,这样它们在数据类型转换时出现问题的可能性最小,然后,一旦可行,尝试添加所有“int”和“character”列......然后添加任何其他列。另外,您要针对哪个数据库。有些数据库不使用“?” 作为命令中的占位符,但使用“命名”参数,有些使用
"actualColumn = @namedCol"
or even
"actualColumn = :namedCol"
希望这能让你度过难关...