使用AutoIncrement列对DataTable.Rows.Add进行ConstraintException

时间:2010-07-06 16:38:45

标签: .net ado.net auto-increment unique-constraint

我有一些带有ID列的DataTables,在MySQL服务器端和ADO.NET架构端都启用了AutoIncrement(从XML模式文件加载)。我不想在插入行时关心这些ID,因为它们唯一的用途是拥有表的主键 - 没有外键引用。但是,当要添加新行时,DataTable已经包含行,即。即ID从1开始的行已驻留在DataTable中。

ID列的默认AutoIncrementSeed值为-1,AutoIncrementStep值为1(仅保留Visual Studio提供的默认值)。如果我只想一次插入两个新行,那么一切似乎都很好,因为当使用dataTable.NewRow()创建它们时,它们获得ID为-1和0.但是如果我想添加第三行,它将获取ID 1由NewRow()分配。随后当我想用dataTable.Rows.Add(...)插入新行时抛出ConstraintException,因为已经存在ID = 1的行。

我认为禁用ADO.NET架构的AutoIncrement内容是没有解决方案的,因为在我使用.Rows.Add()

添加行之前,我仍然需要确保自己ID是唯一的。

这个问题的简单/优雅解决方案是什么?现在我无法想象这是一个非常罕见的任务。

谢谢!

2 个答案:

答案 0 :(得分:1)

解决此问题的一种非常简单的方法是将AutoIncrementStep属性设置为-1 - 然后ID将减少,即-1,-2,-3等。

希望这有帮助, 史蒂夫

答案 1 :(得分:0)

您可以尝试类似于我在下面提供的示例。在添加另一行之前,您可以使用表上的Select来验证唯一列值是否已存在:

using (SqlConnection connection = new SqlConnection(sqlConnectionStr))
        {
            connection.Open();
            // Do work here.
            DataTable userTable = new DataTable("usertable");

            using (SqlCommand sqlCmd = new SqlCommand("select * from [user]"))
            {
                sqlCmd.Connection = connection;
                SqlDataAdapter dataAdapter = new SqlDataAdapter(sqlCmd);
                dataAdapter.Fill(userTable);
            }

            int newUserId = 3;
            DataRow[] selectedRows = userTable.Select(  string.Format( "id={0}", newUserId));
            bool userIdAlreadyTaken = selectedRows.Length > 0 ;
            if( !userIdAlreadyTaken )
            {
                // Add new user
                DataRow newRow = userTable.Rows.Add(new object[] { 3, "John" });
            }
        }