如何使用其他来源的数据更新SQL Server表(DataTable)

时间:2012-02-10 03:18:53

标签: c# asp.net sql-server-2005 datatable sqlbulkcopy

我有一个{。{1}},它是从.xls表生成的。

我想将此DataTable存储到SQL Server数据库中的现有表中。

我使用DataTable来存储唯一PK 的行。

问题是,我还有其他行与SQL Server表具有相同的PK ,但与SQL Server表相比,包含具有不同值的单元格

简而言之:

让我们说SqlBulkCopy我有这样的一行:

id(PK)|名字|编号

005 | abc | 123

006 | lge | 122

我的SQL服务器就像这样;

id(PK)|名字|编号

004 | cbs | 345

005 | lks | 122

现在您可以使用DataTable直接将 006 行上传到SQL Server。另一方面,由于SQL Server表包含具有相同PK的行,因此无法使用它插入行 005

现在我尝试手动提取行。将每个单个单元格提取到ArrayList中,然后生成UPDATE Table语句。但是这个方法似乎不可行,因为我要处理这么多行。

我正在寻找一种更好的方法来实现这一目标。

感谢任何帮助。

感谢的

1 个答案:

答案 0 :(得分:2)

使用以下代码:

C#用于从DataTable读取数据并准备XML数据的侧码:

DataTable dt = new DataTable();
StringBuilder sb = new StringBuilder();

sb.Append("<R>");
for (int i = 0; i < dt.Rows.Count; i++)
{
    sb.Append("<C><ID>" + dt.Rows[0].ToString() + "</ID>");
    sb.Append("<N>" + dt.Rows[1].ToString() + "</N>");
    sb.Append("<I>" + dt.Rows[2].ToString() + "</I></C>");
}

sb.Append("</R>");

///pass XML string to DB side
///
//sb.ToString(); //here u get all data from data table as xml format

数据库端存储过程(您需要更新表名):

CREATE PROCEDURE dbo.UpdateData 
    -- Add the parameters for the stored procedure here
    @data       XML
AS
BEGIN
    SET NOCOUNT ON;

    -- keep data into temp table
    create table #tmp_data (id nchar(2),name varchar(20), number int)

    DECLARE @XMLDocPointer INT  
    EXEC sp_xml_preparedocument @XMLDocPointer OUTPUT, @DATA

    INSERT INTO #tmp_data(id,name,number)
    SELECT  ID,N,I
    FROM OPENXML(@XMLDocPointer,'/R/C',2)
    WITH(
            ID  nchar(30),
            N   VARCHAR(20),
            I   int
        )

    EXEC sp_xml_removedocument @XMLDocPointer

    begin tran
        -------------------INSERT not existing ones
        INSERT INTO TABLE (id,name,number)
        SELECT id,name,number
        FROM #tmp_data
        WHERE NOT EXISTS
        (
            SELECT 1
            FROM TABLE
            WHERE ID = #tmp_data.ID
        )

        --- update existing ones
        UPDATE  TABLE
        SET name = #tmp_data.name, number = #tmp_data.number
        FROM #tmp_data
        WHERE #tmp_data.id = TABLE.id

        commit tran

    if(@@error <> 0)
        rollback tran

END