ADO.. NET数据集主键违规

本文关键字:NET 数据集 ADO | 更新日期: 2023-09-27 18:08:49

我使用DataAdapter来填充具有主键的表中的DataSet

如果我将主键列中的值更改为已经存在于另一行中的值,我不会得到主键冲突错误。

如果我在改变一行后调用DataSet.AcceptChanges(),现在有重复的主键值,仍然没有主键违反错误。

为什么会这样?

string sqlcommand = "select * from itemmaster";//itemaster contains id field which is primary key//
SqlConnection cn = new SqlConnection(connstring);
cn.Open();
SqlCommand cmd = new SqlCommand(sqlcommand, cn);
SqlDataAdapter da = new SqlDataAdapter(cmd);
DataSet ds = new DataSet();
da.Fill(ds);
ds.Tables[0].Rows[4]["ID"] = "2"; // value 2 already exists in another row

ADO.. NET数据集主键违规

要执行任何约束,例如Primary Key约束,您需要告诉DataSet来自源的底层模式。要做到这一点,在填充DataSet之前使用FillSchema()方法:

da.FillSchema(ds, SchemaType.Source);
da.Fill(ds);

DataSet只是一个断开连接的数据集。

当你从数据集中插入、更新或删除行时,你实际上并没有直接更新数据库。您只是将这些更改提交到未连接的数据集。例如,当你这样做时:

ds.Tables[0].Rows[4].Delete();
ds.AcceptChanges();

您在这里所做的只是从Table[0]中删除一行,然后在DataSet中提交更改,而不是在数据库本身。要在数据库中提交此更改,您需要做一些不同的事情。

您需要在DataAdapter中添加"delete命令"。以您的代码为例:

string sqlcommand = "select * from itemmaster";//itemaster contains id field which is primary key//
SqlConnection cn = new SqlConnection(connstring);
cn.Open();
SqlCommand cmd = new SqlCommand(sqlcommand, cn);
SqlDataAdapter da = new SqlDataAdapter(cmd);
SqlCommand deleteCmd = new SqlCommand("DELETE FROM itemmaster WHERE ID = @ID", cn);
SqlParameter deleteParam = deleteCmd.Parameters.Add("@ID", SqlDbType.Int, 4, "ID");
deleteParam.SourceVersion = DataRowVersion.Original;
da.DeleteCommand = deleteCmd;
DataSet ds = new DataSet();
da.FillSchema(ds, SchemaType.Source, "itemmaster");
da.Fill(ds, "itemmaster");
ds.Tables[0].Rows[4].Delete();
da.Update(ds, "itemmaster");

查看更多信息:

使用数据适配器更新数据源