C# 从C更新大量行的有效方法#

C# 从C更新大量行的有效方法#,c#,sql-server,linq,C#,Sql Server,Linq,我有一个程序,在其中打开一个SqlConnection,加载一个对象列表,修改每个对象上的值,然后更新SQL Server数据库中的行。因为修改需要字符串解析,所以我无法用纯t-SQL进行 现在我正在遍历对象列表,并在每次迭代中运行SQL更新。这似乎效率很低,我想知道是否有更有效的方法使用LINQ来实现这一点 该列表称为UsageRecords。我正在更新的值是MthlyConsumption 这是我的密码: foreach (var item in UsageRecords) { st

我有一个程序,在其中打开一个
SqlConnection
,加载一个对象列表,修改每个对象上的值,然后更新SQL Server数据库中的行。因为修改需要字符串解析,所以我无法用纯t-SQL进行

现在我正在遍历对象列表,并在每次迭代中运行SQL更新。这似乎效率很低,我想知道是否有更有效的方法使用LINQ来实现这一点

该列表称为
UsageRecords
。我正在更新的值是
MthlyConsumption

这是我的密码:

foreach (var item in UsageRecords)
{
    string UpdateQuery = @"UPDATE tbl810CTImport 
                           SET MthlyConsumption = " + item.MthlyConsumption +
                           "WHERE ID = " + item.Id;
    SqlCommand update = new SqlCommand(UpdateQuery, sourceConnection);
    update.ExecuteNonQuery();
}
请尝试以下方法:

string UpdateQuery = @"UPDATE tbl810CTImport SET MthlyConsumption = @consumption WHERE ID = @itemId";
var update = new SqlCommand(UpdateQuery, sourceConnection);
update.Parameters.Add("@consumption", SqlDbType.Int); // Specify the correct types here
update.Parameters.Add("@itemId", SqlDbType.Int); // Specify the correct types here
foreach (var item in UsageRecords)
{
    update.Parameters[0].Value = item.MthlyConsumption; 
    update.Parameters[1].Value = item.Id;
    update.ExecuteNonQuery();
}
它应该更快,因为:

  • 您不必每次都创建命令
  • 您不会每次都创建新字符串(串联)
  • 查询不是在每次迭代时都进行分析(只是更改参数值)
  • 它会的。(感谢评论中的@johncarcenter)

    • 在这样的情况下,您无法编写一条更新语句来覆盖所有基础,最好将语句成批处理,一次运行多条语句

      var commandSB = new StringBuilder();
      int batchCount = 0;
      
      using (var updateCommand = sourceConnection.CreateCommand())
      {
          foreach (var item in UsageRecords)
          {
              commandSB.AppendFormat(@"
                  UPDATE tbl810CTImport 
                  SET MthlyConsumption = @MthlyConsumption{0}
                  WHERE ID = @ID{0}", 
                  batchCount
              );
      
              updateCommand.Parameters.AddWithValue(
                  "@MthlyConsumption" + batchCount,
                  item.MthlyConsumption
              );
      
              updateCommand.Parameters.AddWithValue(
                  "@ID" + batchCount,
                  item.MthlyConsumption
              );
      
              if (batchCount == 500) {
                  updateCommand.CommandText = commandSB.ToString();
                  updateCommand.ExecuteNonQuery();
      
                  commandSB.Clear();
                  updateCommand.Parameters.Clear();
                  batchCount = 0;
              }
              else {
                  batchCount++;
              }
          }
      
          if (batchCount != 0) {
              updateCommand.ExecuteNonQuery();
          }
      }
      
      你可以使用

    • -见
    • 或者我之前所做的是以下其中一项:

    • 撕掉有问题的身份证,重新插入
    • 将ID+新值大容量插入临时表,并在SQL server上更新该表:
    • 
      更新u
      设置u.MthlyConsumption=s.MthlyConsumption
      从TBL810C导入u
      内部联接正在运行
      u、 id=s.id
      

      应该像这样简单

      private void button1_Click(object sender, EventArgs e)
              {
                  SqlConnection con = new SqlConnection("Server=YourServerName;Database=YourDataBaseName;Trusted_Connection=True"); 
      
                  try
                  {
                      //cmd new SqlCommand( "UPDATE Stocks 
                      //SET Name = @Name, City = @cit Where FirstName = @fn and LastName = @add";
      
                      cmd = new SqlCommand("Update Stocks set Ask=@Ask, Bid=@Bid, PreviousClose=@PreviousClose, CurrentOpen=@CurrentOpen Where Name=@Name", con);
                      cmd.Parameters.AddWithValue("@Name", textBox1.Text);
                      cmd.Parameters.AddWithValue("@Ask", textBox2.Text);
                      cmd.Parameters.AddWithValue("@Bid", textBox3.Text);
                      cmd.Parameters.AddWithValue("@PreviousClose", textBox4.Text);
                      cmd.Parameters.AddWithValue("@CurrentOpen", textBox5.Text);
                      con.Open();
                      int a = cmd.ExecuteNonQuery();
                      if (a > 0)
                      {
                          MessageBox.Show("Data Updated");
                      }
                  }
                  catch (Exception ex)
                  {
                      MessageBox.Show(ex.Message);
                  }
                  finally
                  {
                      con.Close();
                  }
              }
      

      更改代码以满足您的需要。

      与您的问题无关:,以避免插入,并防止坏字符打断与您的问题相关的查询(如
      字符)。我想这就是你要找的。谢谢。这是一个很好的观点。在我进行测试时,代码中暂时没有SQL文本。@johncarcenter感谢您提供的链接,该链接可能会重复,请注意,这会加快速度approach@JohnCarpenter谢谢我知道那件事,但找不到消息来源。我已经对答案进行了相应的编辑。根据性能与您愿意投入的开发工作量的不同,插入一个暂存表并运行一条更新语句(如我的答案中所示)将是最快的。