读书人

大并发量下的线程数据有关问题

发布时间: 2012-05-12 15:39:31 作者: rapoo

大并发量下的线程数据问题
今天在做性能测试时为了方便知道哪个过程用了多长时间,所以在代码里写了处理时间记录。以提交业务时的时间为开始点,每一个处理过程获取系统时间减开始时间,记录开始时间到处理完当前过程用了多少ms。
然后跑1W个业务过程,每秒上20个,当同时运行过程数达到2K多个时,时间记录出了问题,一个过程完成的每个段的总ms数应是增加的,结果出现了ms数小于前一个处理段ms数的问题。(1000用户并发时没有问题)
400用户并发时的正常过程如下:
加载xml:0 获取信息:0 保存XML:0 评分完成:46 保存XML:46 保存错误数据:187 保存信息到库:187
加载xml:15 获取信息:15 保存XML:15 评分完成:62 保存XML:62 保存错误数据:203 保存信息到库:203

1W用户到达2000并发时会出以如下错误:
加载xml:0 获取信息:0 保存XML:578 评分完成:718 保存XML:0 保存错误数据:828 保存信息到库:828
加载xml:0 获取信息:31 保存XML:703 评分完成:968 保存XML:140 保存错误数据:984 保存信息到库:984
加载xml:0 获取信息:0 保存XML:796 评分完成:921 保存XML:109 保存错误数据:15 保存信息到库:15
加载xml:15 获取信息:15 保存XML:687 评分完成:812 保存XML:15 保存错误数据:15 保存信息到库:15
加载xml:0 获取信息:0 保存XML:343 评分完成:375 保存XML:609 保存错误数据:484 保存信息到库:484


原来担心StringBuilder的线程安全问题,所以把timeInfo由StringBuilder改成了string。
代码基本过程如下:

C# code
using System;class class1{    static StringBuilder infoAll = new StringBuilder();    private void Page_Load()    {        //如果要保存,将信息保存到文件中        if (Request.QueryString["save"] == "1")        {            System.IO.StreamWriter sw = new StreamWriter("c:\\logs\\test\\examcount.txt", true);            sw.WriteLine(timeInfoAll.ToString());            sw.Close();            infoAll = new StringBuilder();            return;        }        //初始化        DateTime dtS = DateTime.Now;        TimeSpan ts = new TimeSpan();        string timeInfo = "";        //过程1        ts = DateTime.Now - dtS;        timeInfo += ";加载xml:" + ts.Milliseconds;        //过程2        ts = DateTime.Now - dtS;        timeInfo += "; 从库获取信息:" + ts.Milliseconds;        //过程3        ts = DateTime.Now - dtS;        timeInfo += "; 保存XML:" + ts.Milliseconds;        if(1=1)//分支条件            Pro1(dtS, timeInfo, ts);        else            Pro1A(dtS, timeInfo, ts);    }    private void Pro1(DateTime dtS, string timeInfo, TimeSpan ts)    {        //过程        Pro2(dtS, timeInfo, ts);    }    private void Pro1A(DateTime dtS, string timeInfo, TimeSpan ts)    {        //过程        Pro2(dtS, timeInfo,ts);    }    private void Pro2(DateTime dtS, string timeInfo, TimeSpan ts)    {        ts = DateTime.Now - dtS;        timeInfo += "; 数据处理完成:" + ts.Milliseconds;        //过程4        ts = DateTime.Now - dtS;        timeInfo += "; 保存XML:" + ts.Milliseconds;        //过程5        ts = DateTime.Now - dtS;        timeInfo += "; 保存错误数据:" + ts.Milliseconds;        //过程6        ts = DateTime.Now - dtS;        timeInfo += "; 保存信息到库:" + ts.Milliseconds + "\r\n";        infoAll.Append(timeInfo);    }}


[解决办法]
个人认为你的日志记录,不是一个用户使用的结果,比如用户A执行了过程一并记录了时间,马上要执行过程2,但是还没有记录时间,这是用户B进入页面并执行过程,这时会写入日志吧,但这个值和用户A的值就不一样了
[解决办法]
孩,用TotalMilliseconds 。
Milliseconds只是指这个时间持续中的毫秒分量。
1000个没问题是因为都不超过1秒,所有怎么减都没错。
超过1秒,你知道的。

读书人网 >C#

热点推荐