C#与数据库的一些效率测试

本文通过测试分析了C#插入数据库的三种方法:直接SQL插入、参数化SQL和DataTable更新,以及查询效率,包括Select Top 1、Select *与指定列。此外,还探讨了多线程并发下数据库访问的性能,并对比了字符串拼接的不同方法。测试结果显示,不同场景下各方法的效率各有优劣,适合的应用场景也不同。

摘要生成于 C知道 ,由 DeepSeek-R1 满血版支持, 前往体验 >

 

数据库效率

 

测试用表:4列,一列为int类型,2varchar1char

 

添加

往数据库里添加数据目前测试了3个方案

1.  根据数据生成sql语句,直接插入

2.  采用sql传参数的方式插入

3.  采用DataTable更新的方法

 

测试结果:

       在插入5000条记录的时候,方案1和方案2的事件都在2.3s~2.4s,方案1比方案2略快一点,方案3事件在12s上下

       从代码的角度上来看,如果可以预知要存储的数据里不带单引号,用方案1还可以再加快一点点数据。不过我倾向使用方案2

 

测试代码:

       方案1:直接生成sql语句

              StringBuilder strSql=new StringBuilder();

              strSql.Append("insert into andString(");

              strSql.Append("ID, string1,string2,string3");

              strSql.Append(")");

              strSql.Append(" values (");

              strSql.Append(""+model.ID.ToString()+",");

              strSql.Append("'"+model.string1.Replace("'", "''") +"',");

              strSql.Append("'"+model.string2.Replace("'", "''") +"',");

              strSql.Append("'"+model.string3.Replace("'", "''") +"'");

              strSql.Append(")");

              DbManagerSQL.ExecuteSql(strSql.ToString());

 

       方案2:传参数

              StringBuilder addstrSql=new StringBuilder();

              addstrSql.Append("insert into andString(");

              addstrSql.Append("ID,string1,string2,string3)");

              addstrSql.Append(" values (");

              addstrSql.Append("@ID,@string1,@string2,@string3)");

              SqlParameter[] parameters = {

                                                   new SqlParameter("@ID", SqlDbType.Int,4),

                                                   new SqlParameter("@string1", SqlDbType.VarChar,200),

                                                   new SqlParameter("@string2", SqlDbType.VarChar,2000),

                                                   new SqlParameter("@string3", SqlDbType.Char,20)};

 

              parameters[0].Value = model.ID;

              parameters[1].Value = model.string1;

              parameters[2].Value = model.string2;

              parameters[3].Value = model.string3;

 

              DbManagerSQL.ExecuteSql(addstrSql.ToString(),parameters);

 

       方案3DataTable更新

              DataRow row = dt.NewRow();

              row["ID"] = model.ID;

              row["string1"] =  model.string1;

              row["string2"] = model.string2;

              row["string3"] = model.string3;

              dt.Rows.Clear();

              dt.Rows.Add(row);

              DbManagerSQL.UpdateTable(dt,tempSql);

 

 

查询

       测试用表:表为添加时的测试用表,表内有30000条记录

 

测试结果:

1.            select top 1方案比用 select 方案在查单条记录时候数据要快很多目前测试的比例是1:2

2.            Select * select 完整列名,就目前的测试结果来看时间比较接近,大约为1:0.8

3.            DataSet里取数据比从DataTable里取数据要快很多,基本上是快一倍,这点很是让人纳闷,包括我在sql查询返回DataSet后只返回DataSettable[0]回去,效率也还是一样的慢,估计问题是出在前台从DataSet取数据的代码经过编译器特别优化了

 

测试代码:

DataSet取数据代码:

              DataSet ds=DbManagerSQL.Query(strSql.ToString(),parameters);

              if(ds.Tables[0].Rows.Count>0)

              {

                   model.ID = (int)ds.Tables[0].Rows[0]["ID"];

                   model.string1=ds.Tables[0].Rows[0]["string1"].ToString();

                   model.string2=ds.Tables[0].Rows[0]["string2"].ToString();

                   model.string3=ds.Tables[0].Rows[0]["string3"].ToString();

                   return model;

              }

              else

              {

                   return null;

         }

 

DataTable取数据代码:

              DataTable dt=DbManagerSQL.QueryTable(strSql.ToString(),parameters);

              if(dt.Rows.Count>0)

              {

                   model.ID = (int)dt.Rows[0]["ID"];

                   model.string1=dt.Rows[0]["string1"].ToString();

                   model.string2=dt.Rows[0]["string2"].ToString();

                   model.string3=dt.Rows[0]["string3"].ToString();

                   return model;

              }

              else

              {

                   return null;

         }

 

 

多线程并发数据库访问效率:

测试环境:还是用上面的表,采用直接插入Sql语句方式添加数据,每个线程在测试时插入3次,每次插入1000条数据。底层的数据库访问采用2种访问方式,一个是为每次连接创建一个数据库连接, 另外一个是所用数据库访问都采用同一个连接,每次访问时用线程互斥的进行使用。网络采用100M交换机组网的公司网络。

 

 

测试结果:

       数据库与测试程序在同一台电脑

线程

单连接

多连接

时间

cpu

时间

cpu

10

4s

100%

3~4

100%

20

8~9

100%

20~24

5%

30

13~15s

100%

20~24

5%

50

24~27

100%

28~30

25%

70

35~39

100%

37~43

40%

      

       数据库与测试程序不在同一台电脑

线程

单连接

 

多连接

 

时间

cpu

网卡

时间

cpu

网卡

10

12s

10%

5%

4

5%

13%

20

25s

10%

5%

11~13

5%

8%

30

32~38s

15%

5%

19~20

5%

9%

50

55~65

15%

5%

24~27

15%

11%

70

80~90

20%

5%

29~32

40%

13%

 

从测试的数据来看单连接和多连接并不能说那一个更好,只能说要根据实际应用的情况来选择实际连接方式,因为目前还没有使用连接池的C#代码,所以没有针对连接池方案进行测试。

 

 

在并发条件下优化查询最佳的方案应该是优化数据库

在数据库与应用程序分离的时候进行并发查询操作,发现提高查询数据的瓶颈不在应用程序,而是在数据库。

 

 

字符串效率

       在生成数据sql语句的时候,要将多个参数合并到一个sql语句中,常用的方法有4

1.  字符串直接相加

2.  Replace

3.  Format

4.  Stringbuffer

 

反正不管怎么比较方案1的字符串直接相加法绝对绝对是慢的,但也是最容易理解的,建议能用其他方法替换就尽量不用。

方案2和方案3一般用来替换sql语句里的参数,不适用于字符串连接。如果只是需要替换一个字符串,用Replace比较合适,速度比Format20%,如果要替换2个以上的字符串就只使用Format方法

用方案1和方案2连接字符串,效率相差可以达到20倍,连接的字符串越多StringBuffer越显示出它的效率来,不过可惜的是在连接5个以下字符串的时候,他们的效率差不多。

 

 

评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值