zoukankan      html  css  js  c++  java
  • ASP.NET批量更新数据/批量插入数据 带事务

    优化前:

    批量对1000条数据的进行插入 和 更新的操作~执行速度慢(表数据量大,字段多~~这不在本文优化之内,另外优化处理~~~),也没有等待提示~~点一下等好久没任何反应~~半天过去了 提示操成功~~脾气躁一点 啪啪啪点几下 系统卡死GG了~~

    优化后:

    执行时加入操作等待提示~~执行后增加耗时展示~~但这都不是本文重点~~略过~~

    大概看了下现有的程序对1000条数据打执行,就是循环1000个更改+1000个插入~根数据库交互2000次~~不慢才怪~~

    批量更新:使用SqlDataAdapter.Update(DateTable)

    批量插入:使用SqlBulkCopy

    都9012年了还ado.net ~~不过执行效率确实提高一倍以上~~不知道这代码还有没有人去用了 ~~

    demo奉上~~~

    using System;
    using System.Collections.Generic;
    using System.Data;
    using System.Data.SqlClient;
    using System.Linq;
    using System.Text;
    using System.Threading.Tasks;
    
    namespace 批量插入更新数据
    {
        class Program
        {
            static void Main(string[] args)
            {
                DateTime dt1 = System.DateTime.Now;
                string connStr = @"server=SHENSQL2012;uid=sa;pwd=123456;database=LmhsDB";
                using (SqlConnection con = new SqlConnection(connStr))
                {
                    con.Open();
                    SqlTransaction tran = con.BeginTransaction();
                    try
                    {
                        //批量插入
                        Inserts(con, tran);
                        Updates(con, tran);
                        tran.Commit();
                    }
                    catch
                    {
                        tran.Rollback();
                    }   
                }
                DateTime dt2 = System.DateTime.Now;
                TimeSpan ts = dt2.Subtract(dt1);
                Console.WriteLine("耗时:" + Convert.ToDouble(ts.TotalMilliseconds / 1000) + "");
                Console.ReadLine();
            }
    
            public static void Inserts(SqlConnection con, SqlTransaction tran)
            {
                DataTable dtIns = new DataTable();
                //首先查出一张空表 作为模版(注意主键自增问题:SqlBulkCopyOptions.KeepNulls)
                SqlCommand sqlIns = new SqlCommand("select ID,UserName,Gender,CreateTime "
                                   + "  FROM InsertTest where 1=0 ", con, tran);
                SqlDataAdapter sdaIns = new SqlDataAdapter();
                sdaIns.SelectCommand = sqlIns;
                sdaIns.Fill(dtIns);
                //插入1000条
                for (int i = 0; i < 1000; i++)
                {
                    DataRow dataRow = dtIns.NewRow();
                    dataRow[0] = 0;
                    dataRow[1] = "我叫" + Guid.NewGuid();
                    dataRow[2] = "";
                    dataRow[3] = DateTime.Now;
                    dtIns.Rows.Add(dataRow);
                }
                using (SqlBulkCopy sqlBulkIns = new SqlBulkCopy(con, SqlBulkCopyOptions.KeepNulls, tran))
                {
                    sqlBulkIns.DestinationTableName = "InsertTest";
                    sqlBulkIns.BatchSize = dtIns.Rows.Count;
                    if (dtIns != null && dtIns.Rows.Count != 0)
                    {
                        sqlBulkIns.WriteToServer(dtIns);
                    }
                }
                sqlIns.Dispose();
            }
    
            public static void Updates(SqlConnection con, SqlTransaction tran)
            {
                DataSet ds = new DataSet();
                SqlDataAdapter sda = new SqlDataAdapter();
                //先查询出一个模版放到DataSet,让更新Dataset中打数据 然后SqlDataAdapter.Update(Table)批量更新
                SqlCommand sqlCommandSel = new SqlCommand("select top 1000 ID,UserName,Gender,CreateTime from  InsertTest  ", con, tran);
                sda.SelectCommand = sqlCommandSel;
                sda.Fill(ds);
                SqlCommand sqlCommandUp = new SqlCommand("Update InsertTest set UserName=@UserName,Gender=@Gender,CreateTime=@CreateTime where ID=@ID", con, tran);
                sda.UpdateCommand = sqlCommandUp;
                sda.UpdateCommand.Parameters.Add("@UserName", SqlDbType.VarChar, 100, "UserName");
                sda.UpdateCommand.Parameters.Add("@Gender", SqlDbType.VarChar, 100, "Gender");
                sda.UpdateCommand.Parameters.Add("@CreateTime", SqlDbType.DateTime, 0, "CreateTime");
                sda.UpdateCommand.Parameters.Add("@ID", SqlDbType.NVarChar, 0, "ID");
                sda.UpdateCommand.UpdatedRowSource = UpdateRowSource.None;
                sda.UpdateBatchSize = 0;
    
                //把模版中的数据修改后更新回去,实际上应该是你更新的业务数据集合
                for (int count = 0; count < ds.Tables[0].Rows.Count; count++)
                {
                    //对 System.Data.DataRow 对象开始编辑操作。
                    ds.Tables[0].Rows[count].BeginEdit(); 
                    ds.Tables[0].Rows[count]["UserName"] ="我是批量更改过的";
                    ds.Tables[0].Rows[count]["Gender"] = "男-批量更新的";
                    ds.Tables[0].Rows[count]["CreateTime"] = DateTime.Now;
                    ds.Tables[0].Rows[count]["ID"] = ds.Tables[0].Rows[count]["ID"];//必须要保证dt中的Id在数据表中存在,否则会报错,比如dt中的Id=1000,那么数据表中也需要有一条Id=1000的数据
                    ds.Tables[0].Rows[count].EndEdit();
    
                }
                int aa = sda.Update(ds.Tables[0]);
                sqlCommandSel.Dispose();
                sqlCommandUp.Dispose();
    
            }
    
    
    
    
    
    
        }
    }

     https://gitee.com/pfr/InsertsOrUpdate  

    企鹅群:48904756

  • 相关阅读:
    使用Eclipse进行远程调试【转】
    JRE_HOME environment variable is not defined correctly This environment variableis needed to run this program
    Window 通过cmd查看端口占用、相应进程、杀死进程等的命令【转】
    A cycle was detected in the build path of project
    调用CXF工具 生成 WSDL【转】
    解决cxf+spring发布的webservice,types,portType和message以import方式导入
    Target runtime com.genuitec.runtime.generic.jee50 is not defined
    修改eclipse启动时eclipse使用的jre
    JAVA中堆栈和内存分配原理
    JVM -Xss调整Stack Space的大小 【转】
  • 原文地址:https://www.cnblogs.com/pingfanren/p/12398094.html
Copyright © 2011-2022 走看看