首页新闻找找看学习计划

C# 使用SqlDataAdapter批量更新数据,出现当传递具有新行的 DataRow 集合时,更新要求有效的 InsertCommand

0
悬赏园豆:10 [已解决问题] 解决于 2019-04-25 11:43

C# 使用SqlDataAdapter批量更新数据,出现当传递具有新行的 DataRow 集合时,更新要求有效的 InsertCommand,代码如下:
System.Data.SqlClient.SqlDataAdapter sda = new System.Data.SqlClient.SqlDataAdapter();
SqlCommandBuilder objcmdBuilder;
SqlCommand scmd = new SqlCommand();//定义一个SqlCommand的实例,以便绑定
scmd.CommandType = CommandType.Text;
scmd.Connection = new SqlConnection(GetConnectionStrings());
scmd.Parameters.Add("@Id", SqlDbType.VarChar, 50, "Id");
scmd.Parameters.Add("@PayId", SqlDbType.VarChar, 50, "PayId");
scmd.Parameters.Add("@CostCenterName", SqlDbType.VarChar, 50, "CostCenterName");
scmd.Parameters.Add("@Name", SqlDbType.NVarChar, 8000, "Name");
scmd.Parameters.Add("@WorkNumber", SqlDbType.VarChar, 50, "WorkNumber");
scmd.Parameters.Add("@PayMonth", SqlDbType.VarChar, 50, "PayMonth");
scmd.CommandText = string.Format(@"
UPDATE HouGe_PaySheedDetail SET
CostCenterName=@CostCenterName,
Name=@Name,
WorkNumber=@WorkNumber,
PayMonth=@PayMonth
where Id=@Id");
sda.UpdateCommand = scmd;
sda.Update(dt);// 此处的dt是从其他地方传过来的,是需要更新到数据库中的,错误就发生在这个地方,试过很多方法都不行,网上的很多方法也都是不行,有谁做过这样的操作呢??
sda.Dispose();

C#
gyangjing的主页 gyangjing | 初学一级 | 园豆:11
提问于:2019-04-18 18:02
< >
分享
最佳答案
0

现在我研究出了一种效率比较高的方法,来实现大批量数据更新的问题,代码如下:
/// <summary>
/// 批量更新
/// </summary>
/// <param name="dt"></param>
/// <param name="columName"></param>
/// <param name="tableName"></param>
/// <param name="primaryKey"></param>
public void BatchUpdate(DataTable dt, string[] columName, string tableName, string primaryKey)
{
using (SqlCommand command = new SqlCommand("", _sqlConnection))
{
try
{
var tempTableName = $"#Temp{DateTime.Now.ToString("yyyMMddHHmmss")}";
var updateSetSql = new StringBuilder();
var updateFormSql = new StringBuilder();
updateSetSql.AppendFormat(@" UPDATE A SET");
foreach (var item in columName)
{
updateSetSql.AppendFormat(@" A." + item + "=Temp." + item + ",");
}
var str = updateSetSql.ToString();
str = str.Substring(0, str.Length - 1);
updateSetSql.Remove(0, updateSetSql.Length);
updateFormSql.AppendFormat(str);
updateFormSql.AppendFormat(@" FROM " + tableName + " A ");
updateFormSql.AppendFormat(@" INNER JOIN " + tempTableName + " Temp ");
updateFormSql.AppendFormat(@" ON A." + primaryKey + "=Temp." + primaryKey + ";");
updateFormSql.AppendFormat(@" DROP TABLE " + tempTableName + " ");
command.Transaction = _sqlTransaction;
//构建临时表
command.CommandText = $"SELECT * INTO {tempTableName} FROM " + tableName + " WHERE 1 = 2;";
command.ExecuteNonQuery();

                //插入临时表
                using (SqlBulkCopy bulkCopy = new SqlBulkCopy(_sqlConnection, SqlBulkCopyOptions.KeepIdentity, _sqlTransaction))
                {
                    bulkCopy.DestinationTableName = tempTableName;
                    bulkCopy.BatchSize = dt.Rows.Count;
                    if (dt != null && dt.Rows.Count != 0)
                    {
                        for (int i = 0; i < dt.Columns.Count; i++)
                        {
                            bulkCopy.ColumnMappings.Add(dt.Columns[i].ColumnName, dt.Columns[i].ColumnName);
                        }
                        bulkCopy.WriteToServer(dt);
                        bulkCopy.Close();
                    }
                }

                //从临时表更新到原表,并删除临时表
                command.CommandTimeout = 300;
                command.CommandText = updateFormSql.ToString();
                command.ExecuteNonQuery();
            }
            catch (Exception ex)
            {
                //throw ex;
            }
            finally
            {
                //conn.Close();
            }
        }
    }
gyangjing | 初学一级 |园豆:11 | 2019-04-25 11:29
其他回答(2)
0

把dt中的数据行状态(DataRowState)改成Modified试试

收获园豆:10
会长 | 园豆:5534 (大侠五级) | 2019-04-18 18:17

哦,这个试过了,但是这个字段是只读的,不可修改。还有没有其他更好的方法来批量Update数据呢?

支持(0) 反对(0) gyangjing | 园豆:11 (初学一级) | 2019-04-18 20:38

@gyangjing: dt.Rows[0].SetModified();

支持(1) 反对(0) 会长 | 园豆:5534 (大侠五级) | 2019-04-19 09:34

@会长: 嗯,这个试过了,是这样改变状态的,不过这种方法执行的效率很低,我又想出了一个折中的办法,能提高不少效率

支持(0) 反对(0) gyangjing | 园豆:11 (初学一级) | 2019-04-25 11:26
0

Sqlcommandbuilder类没有正确使用,需要一个查询语句为基础实例化

慢慢求学路 | 园豆:217 (菜鸟二级) | 2019-04-18 23:05

那个查询语句是必须要的吗?

支持(0) 反对(0) gyangjing | 园豆:11 (初学一级) | 2019-04-19 08:56
清除回答草稿
   您需要登录以后才能回答,未注册用户请先注册