如何以有效的方式覆盖数据库中的重复数据?

时间:2011-12-16 17:58:12

标签: sql-server database sql-server-2008 ado.net

我使用Sql server 2008来存储我的数据,以及像

那样的表结构
index float  not null,
type int   not null,
value int  not null,

和(index,type)是唯一的。没有两个数据具有相同的索引和相同的类型。

所以当我将数据插入表时,我必须检查(索引,类型)对是否在表中,如果它存在我使用update语句,否则,我直接插入它。但我认为这是不是一种有效的方式,因为:

  1. 表中不存在大多数数据'索引​​类型对。因此选择操作是浪费,特别是表格很大。

  2. 当我使用C#或其他CLR语言插入数据时,我无法使用批量复制或批量插入。

  3. 有没有办法直接覆盖数据而不检查它是否存在于表中?

3 个答案:

答案 0 :(得分:4)

如果要更新或插入数据,则需要使用merge

merge MyTable t using (select @index index, @type type, @value value) s on
    t.index = s.index
    and t.type = s.type
when not matched insert (index, type value) values (s.index, s.type, s.value)
when matched update set value = s.value;

这将查看您的值并采取适当的措施。

要在C#中执行此操作,您必须使用传统的SqlClient

SqlConnection conn = new SqlConnection("Data Source=dbserver;Initial Catalog=dbname;Integrated Security=SSPI;");
SqlCommand comm = new SqlCommand();
conn.Open();
comm.Connection = conn;

//Add in your values here
comm.Parameters.AddWithValue("@index", index);
comm.Parameters.AddWithValue("@type", type);
comm.Parameters.AddWithValue("@value", value);

comm.CommandText = 
    "merge MyTable t using (select @index index, @type type, @value value) s on " +
        "t.index = s.index and t.type = s.type " +
    "when not matched insert (index, type value) values (s.index, s.type, s.value) " +
    "when matched update set value = s.value;"
comm.ExecuteNonQuery();

comm.Dispose();
conn.Close();
conn.Dispose();

答案 1 :(得分:0)

您应该将(index, type)变为composite primary key(又名复合键)。

这将确保表甚至只能具有这些唯一的对(我假设表中没有主键)。

如果表格中有主键,您可以在效果相似的列上添加UNIQUE constraint

一旦定义,这意味着任何插入重复对的尝试都将失败。

答案 2 :(得分:0)

其他答案建议约束。创建约束只意味着您将执行触发错误的插入语句。下一步(在创建约束之后)类似INSERT ON DUPLICATE KEY UPDATE,显然确实有一个Sql Server等效。