使用参数Sql Server插入多行

时间:2016-07-22 08:40:08

标签: c# sql-server database sql-server-2008

我试图找出是否有办法在使用参数时在Sql Server中执行多值插入,确切地说,有这样的命令:

com = new SqlCommand("insert into myTable values (@recID,@tagID)", con);
com.Parameters.Add("@recID", SqlDbType.Int).Value = recID;
com.Parameters.Add("@tagID", SqlDbType.Int).Value = tagID;
com.ExecuteNonQuery();

是否有办法使用参数执行多值单插入,并考虑到每个值的参数可能不同? (例如:tagID可能总是不同)

我一直在互联网上搜索但到目前为止没有运气,在此先感谢,问候。

2 个答案:

答案 0 :(得分:7)

您可以使用表值参数:How to pass table value parameters to stored procedure from .net code

首先,在SQL Server中创建类型:

CREATE TYPE [dbo].[myTvpType] AS TABLE 
(
    [RecordID] int,
    [TagID] int
)

用于插入数据的C#代码:

internal void InsertData(SqlConnection connection, Dictionary<int, int> valuesToInsert)
{
    using (DataTable myTvpTable = CreateDataTable(valuesToInsert))
    using (SqlCommand cmd = connection.CreateCommand())
    {
        cmd.CommandText = "INSERT INTO myTable SELECT RecordID, TagID FROM @myValues";
        cmd.CommandType = CommandType.Text;

        SqlParameter parameter = cmd.Parameters.AddWithValue("@myValues", myTvpTable);
        parameter.SqlDbType = SqlDbType.Structured;

        cmd.ExecuteNonQuery();
    }
}

private DataTable CreateDataTable(Dictionary<int, int> valuesToInsert)
{
    // Initialize the DataTable
    DataTable myTvpTable = new DataTable();
    myTvpTable.Columns.Add("RecordID", typeof(int));
    myTvpTable.Columns.Add("TagID", typeof(int));

    // Populate DataTable with data
    foreach(key in valuesToInsert.Key)
    {
        DataRow row = myTvpTable.NewRow();
        row["RecordID"] = valuesToInsert[key];
        row["TagID"] = key;
    }
}

答案 1 :(得分:0)

您可以通过将数据作为xml字符串发送并转换为sql中存储过程中的表来完成此操作。例如: 假设我在sql表中发送多行来添加/更新,那么步骤如下:

  1. 使用以下方法将您的类或类列表转换为xml字符串:

    public static string SerializeObjectToXmlString(object value)
    
              {
              var emptyNamepsaces = new XmlSerializerNamespaces(new[] { 
                                        XmlQualifiedName.Empty });
    
        var serializer = new XmlSerializer(value.GetType());
        var settings = new XmlWriterSettings();
        settings.Indent = true;
        settings.OmitXmlDeclaration = true;
    
        using (var stream = new StringWriter())
        using (var writer = XmlWriter.Create(stream, settings))
        {
            serializer.Serialize(writer, value, emptyNamepsaces);
            return stream.ToString();
        }
    }
    
  2. 现在,在将数据发送到数据库时,将您的类对象转换为xml string(这里我在我的代码中使用实体框架,你可以在不使用它的情况下执行此操作):

    bool AddUpdateData(List<MyClass> data)
    {
        bool returnResult = false;
        string datatXml = Helper.SerializeObjectToXmlString(data);
        var sqlparam = new List<SqlParameter>()
                     {
       new SqlParameter() { ParameterName = "dataXml", Value = datatXml}
    
                     };
        var result = this.myEntity.Repository<SQL_StoredProc_ComplexType>().ExecuteStoredProc("SQL_StoredProc", sqlparam);
        if (result != null && result.Count() > 0)
        {
            returnResult = result[0].Status == 1 ? true : false;
        }
        return returnResult;
    }
    
  3. 现在您的SQL代码:

  4. 3.1声明表变量:

    DECLARE @tableVariableName TABLE
    (
        ID INT, Name VARCHAR(20)
    )
    

    3.2将xml字符串插入表变量

    INSERT INTO @tableVariableName
    SELECT 
        Finaldata.R.value ('(ID/text())[1]', 'INT') AS ID, 
        Finaldata.R.value ('(Name/text())[1]', 'VARCHAR(20)') AS Name
    FROM @MyInputXmlString.nodes ('//ArrayMyClass/MyClass') AS Finaldata (R)
    

    3.3最后将此表值插入到sql表中

    INSERT INTO MyTable (ID, Name)                  
    SELECT ID, Name          
    FROM @tableVariableName
    

    这将节省您使用for循环一次又一次地重击数据库的努力。

    希望它能帮到你