最新文章专题视频专题问答1问答10问答100问答1000问答2000关键字专题1关键字专题50关键字专题500关键字专题1500TAG最新视频文章推荐1 推荐3 推荐5 推荐7 推荐9 推荐11 推荐13 推荐15 推荐17 推荐19 推荐21 推荐23 推荐25 推荐27 推荐29 推荐31 推荐33 推荐35 推荐37视频文章20视频文章30视频文章40视频文章50视频文章60 视频文章70视频文章80视频文章90视频文章100视频文章120视频文章140 视频2关键字专题关键字专题tag2tag3文章专题文章专题2文章索引1文章索引2文章索引3文章索引4文章索引5123456789101112131415文章专题3
当前位置: 首页 - 科技 - 知识百科 - 正文

单数据库,多数据库,单实例,多实例不同情况下的数据访问效率测

来源:动视网 责编:小采 时间:2020-11-09 08:13:40
文档

单数据库,多数据库,单实例,多实例不同情况下的数据访问效率测

单数据库,多数据库,单实例,多实例不同情况下的数据访问效率测:最近公司的项目准备优化一下系统的性能,希望在数据库方面看有没有提升的空间,目前压力测试发现数据库服务器压力还不够大,Web服务器压力也不是很大的情况下,前台页面访问却很慢,看有没有办法充分利用数据库服务器的性能,于是做了一个单数据库,多数据库
推荐度:
导读单数据库,多数据库,单实例,多实例不同情况下的数据访问效率测:最近公司的项目准备优化一下系统的性能,希望在数据库方面看有没有提升的空间,目前压力测试发现数据库服务器压力还不够大,Web服务器压力也不是很大的情况下,前台页面访问却很慢,看有没有办法充分利用数据库服务器的性能,于是做了一个单数据库,多数据库


最近公司的项目准备优化一下系统的性能,希望在数据库方面看有没有提升的空间,目前压力测试发现数据库服务器压力还不够大,Web服务器压力也不是很大的情况下,前台页面访问却很慢,看有没有办法充分利用数据库服务器的性能,于是做了一个单数据库,多数据库

最近公司的项目准备优化一下系统的性能,希望在数据库方面看有没有提升的空间,目前压力测试发现数据库服务器压力还不够大,Web服务器压力也不是很大的情况下,前台页面访问却很慢,看有没有办法充分利用数据库服务器的性能,于是做了一个单数据库,多数据库,单实例,多实例不同情况下的数据访问效率测试。

测试环境:

  • CPU:Inter Core2 Quad,Q8300,2.50GHz;
  • 内存:4.00GB
  • 系统:Windows 7 32位系统
  • 数据库系统:SqlServer 2008,有两个实例,一个是默认实例,一个是命名实例QE2
  • 测试数据:

    67万真实的基金收益数据,将这个表的数据放到了3个数据库中,详细内容见下面的连接字符串配置:



    测试内容:

    首先筛选出表中所有的基金代码,然后统计每只基金的最新收益率日期,对应的T-SQL代码如下:


    declare @max_fsrq datetime
    declare @currJJDM varchar(10)
    declare @temp table (jjdm2 varchar(10))
    declare @useTime datetime
    set @useTime =GETDATE ();

    insert into @temp(jjdm2)
    select jjdm from [FundYield] group by jjdm order by jjdm asc

    while EXISTS (select jjdm2 from @temp)
    begin
    set @currJJDM=(select top 1 jjdm2 from @temp)
    select @max_fsrq = MAX(fsrq) from [FundYield] where jjdm=@currJJDM
    delete from @temp where jjdm2 =@currJJDM
    print @max_fsrq
    end

    print 'T-SQL Execute Times(ms):'
    print datediff(ms,@useTime,getdate())

    直接执行这个T-SQL脚本,在数据库表没有索引的情况下,耗费的时间是:

    T-SQL Execute Times(ms):
    58796

    根据这个功能,写了一个.net控制台程序来测试,测试程序没有使用任何数据访问框架,直接使用ADO.NET,下面是多线程测试的代码,其它代码略:

    public static void Test2(string connName1,string connName2)
    {
    System.Diagnostics.Stopwatch watch = new System.Diagnostics.Stopwatch();
    watch.Start();
    string allJjdmList = "";
    string connString = getConnectionString();
    //SqlConnection conn = new SqlConnection(connString);
    //conn.Open();

    string sql = "select jjdm from [FundYield] group by jjdm order by jjdm asc";
    DataSet ds = getData(connString, sql);
    int allCount = ds.Tables[0].Rows.Count;
    int p = (int)(allCount * 0.5);

    System.Threading.Thread t1=new System.Threading.Thread (new System.Threading.ParameterizedThreadStart (tp1=>
    {
    for (int i = 0; i < p; i++)
    {
    string jjdm = ds.Tables[0].Rows[i][0].ToString();

    object result = getSclar(ConfigurationManager.ConnectionStrings[connName1].ConnectionString,
    string.Format("select MAX(fsrq) from [FundYield] where jjdm='{0}'", jjdm));
    if (result != DBNull.Value)
    {
    DateTime dt = Convert.ToDateTime(result);
    //Console.WriteLine("Thread 2 No {0} ,jjdm[{1}] last FSRQ is:{2}", i, jjdm, dt);
    }

    allJjdmList = allJjdmList + "," + jjdm;
    }

    Console.WriteLine("Tread 1 used all time is(ms):{0}", watch.ElapsedMilliseconds);
    }
    ));

    System.Threading.Thread t2 = new System.Threading.Thread(new System.Threading.ParameterizedThreadStart(tp2 =>
    {
    for (int i = p; i < allCount; i++)
    {
    string jjdm = ds.Tables[0].Rows[i][0].ToString();
    //这里不论使用default还是express,区别不大
    object result = getSclar(ConfigurationManager.ConnectionStrings[connName2].ConnectionString,
    string.Format("select MAX(fsrq) from [FundYield] where jjdm='{0}'", jjdm));
    if (result != DBNull.Value)
    {
    DateTime dt = Convert.ToDateTime(result);
    //Console.WriteLine("Thread 2 No {0} ,jjdm[{1}] last FSRQ is:{2}", i, jjdm, dt);
    }

    allJjdmList = allJjdmList + "," + jjdm;
    }

    Console.WriteLine("Tread 2 used all time is(ms):{0}", watch.ElapsedMilliseconds);
    }
    ));

    t1.Start();
    t2.Start();
    t1.Join();
    t2.Join();

    Console.WriteLine("====All thread completed!========");

    }

    下面是测试结果:

    第一次,数据库没有创建索引,进行全表扫描:

    ------单数据库,单线程测试---------
    used all time is(ms):59916
    ------同一实例,双数据库,单线程测试---------
    used all time is(ms):59150
    ------同一实例,双数据库,多线程测试---------
    Tread 2 used all time is(ms):51223
    Tread 1 used all time is(ms):58175
    ====All thread completed!========
    ------双实例,双数据库,单线程测试---------
    used all time is(ms):58230
    ------双实例,双数据库,多线程测试---------
    Tread 2 used all time is(ms):52705
    Tread 1 used all time is(ms):58293
    ====All thread completed!========

    第二次,数据库响应的字段创建索引,下面是测试结果:


    ------单数据库,单线程测试---------
    used all time is(ms):1721
    ------同一实例,双数据库,单线程测试---------
    used all time is(ms):1737
    ------同一实例,双数据库,多线程测试---------
    Tread 2 used all time is(ms):1684
    Tread 1 used all time is(ms):1714
    ====All thread completed!========
    ------双实例,双数据库,单线程测试---------
    used all time is(ms):1874


    ------单数据库,单线程测试---------
    used all time is(ms):1699
    ------同一实例,双数据库,单线程测试---------
    used all time is(ms):1754
    ------同一实例,双数据库,多线程测试---------
    Tread 1 used all time is(ms):1043
    Tread 2 used all time is(ms):1103
    ====All thread completed!========
    ------双实例,双数据库,单线程测试---------
    used all time is(ms):1838
    ------双实例,双数据库,多线程测试---------
    Tread 1 used all time is(ms):1072
    Tread 2 used all time is(ms):1139
    ====All thread completed!========

    测试结论:

    综合全表扫描访问和有索引方式的访问,

    单线程访问:

  • 在同一个数据库实例上,双数据库没有体现出优势,甚至单数据库稍微优胜于多数据库;
  • 在两个数据库实例上,双实例双实例要落后于单实例单数据库;
  • 多线程访问:

  • 双数据库实例稍微落后于单数据库实例;
  • 综合结论,看来不论是双数据库还是双实例,对比与单实例或者单数据库,都没有体现出优势,看来前者的优势不在于访问效率,一位朋友说,数据库实例是不同的服务,控制粒度更小,维护影响比较低。但我想,双数据库实例,双数据库,多核CPU,应该跟两台数据库服务器差不多的性能吧,怎么没有体现优势呢?也许是我的测试机器仅仅有一个磁盘,这里磁盘IO成了瓶颈。

    这个测试有没有意义,或者这个结果的原因,还请大牛们多多指教!

    --------------------------------------------------------------

    意外发现:

    1,有人说频繁的查询在完全数据库中进行效率最高,测试发现,在查询分析器上直接运行上面的那个T-SQL脚本,跟程序从数据库取出数据,再加工计算查询,效率上没有明显的区别,所以哪些支持“将复杂的业务逻辑写在存储过程中效率最高的观点是站不住脚的!” ,ADO.NET从数据库来回操作数据一样有效率,如果加上复杂的字符函数计算和大批量的循环操作,存储过程的效率不一定高。

    2,在使用程序进行频繁的数据库操作的时候,使用一个连接对象还是在每个方法中使用新的连接对象,一直是很纠结的问题,心想频繁的数据操作还是用一个连接对象快吧?在本文给出的测试代码中,有下列语句:

    //SqlConnection conn = new SqlConnection(connString);
    //conn.Open();
    注释掉这些语句,在被调用的方法中使用自己的连接对象,与取消注释,全部使用一个连接对象,效率上没有任何区别!

    究其原因,可能是ADO.NET自动使用了连接池,实际上程序在不同的情况下,使用的都是一个连接,所以操作上效率没有区别。

    后续测试

    在真正的服务器上进行测试,发现测试结论又不一样,我们有服务器A,拥有16个核,32G内存,另外一台服务器B,拥有8个核,16G内存。在服务器A上有一个SqlServer实例,两个一样的数据库;在在服务器B上有一个SqlServer实例,一个数据库,下面是测试结果:

    ------单数据库,单线程测试---------
    used all time is(ms):650
    ------同一实例,双数据库,单线程测试---------
    used all time is(ms):418
    ------同一实例,双数据库,多线程测试---------
    Tread 2 used all time is(ms):221
    Tread 1 used all time is(ms):223
    ====All thread completed!========
    ------双实例,双数据库,单线程测试---------
    used all time is(ms):1283
    ------双实例,双数据库,多线程测试---------
    Tread 1 used all time is(ms):228
    Tread 2 used all time is(ms):542
    ====All thread completed!========

    可以看到,同一实例,多数据库,还是有明显的优势,而多线程优势更大;由于两台服务器性能差距较大,双实例测试没有显示出优势,但多线程下还是比单实例单数据库好!

    为什么PC机跟服务器测试的结论不一致?也许还是跟计算能力相关,PC机的计算负载太大,已经失去了测试的意义。

    文档

    单数据库,多数据库,单实例,多实例不同情况下的数据访问效率测

    单数据库,多数据库,单实例,多实例不同情况下的数据访问效率测:最近公司的项目准备优化一下系统的性能,希望在数据库方面看有没有提升的空间,目前压力测试发现数据库服务器压力还不够大,Web服务器压力也不是很大的情况下,前台页面访问却很慢,看有没有办法充分利用数据库服务器的性能,于是做了一个单数据库,多数据库
    推荐度:
    标签: 数据 效率 访问
    • 热门焦点

    最新推荐

    猜你喜欢

    热门推荐

    专题
    Top