CSDN首页 空间 新闻 论坛 Blog 下载 读书 网摘 搜索 .NET Java 视频 接项目 求职 在线学习 买书 程序员 通知
不看会后悔的Windows XP之经验谈 简单快捷DIY实用家庭影院
CSDN社区
搜索 收藏 打印 关闭
CSDN社区 >  .NET技术 >  C#

多线程问题

楼主chrislv(小吕)2006-08-14 20:48:41 在 .NET技术 / C# 提问

正在做一个指纹比对的程序,分为客户端和服务端。客户端上传指纹数据到服务端进行比较,客户端大概有1000多条数据,服务端大概有几十万条数据。如果不采用多线程这将会是一个十几小时的工作。想用多线程来摆脱困境。现在只是在客户端加几十条数据,我加上多线程之后发现比单线程还要慢,望请各位大虾帮帮小弟  
  public   void   Sync()  
  {  
   
  try  
  {  
  int   CacheSize=CacheCount;  
  int   Score=8;  
  int   ProcessNum=0;  
  DataTable[]   dataarr=new   DataTable[RecordCount/(PagerCount==0?RecordCount:PagerCount)];  
  DataSet   dsSource=new   DataSet();  
  DateTime   dt1=DateTime.Now;  
  this.Refresh();  
  DateTime   dts=DateTime.Now;  
  if(ProgressBarForm.LogFlag)  
  log.Write("----------Step   1:开始读取FP服务器时间:"+dts+"--------------------\r\n");  
  this.Refresh();  
  dataarr[0]=CandAdditional_FP.GetAllFinger(this.RecordCount);  
  recordCount=dataarr[0].Rows.Count;  
  k=new   int[(RecordCount/CacheSize)+(RecordCount%CacheSize!=0?1:0)];    
  for(int   j=0;j<k.Length;j++)  
  {  
  k[j]=axZKFPEngX2.CreateFPCacheDB();//创建指纹比对缓存  
  }  
  DateTime   dte=DateTime.Now;  
  log.Write("----------Step   1:结束读取FP服务器时间:"+dte+",共花了:"+new   DateTime(dte.Ticks-dts.Ticks).ToString("mm:ss.mmm")+"\r\n");  
  DateTime   CacheTimeS=DateTime.Now;  
  dts=DateTime.Now;  
  int   t=-1;  
  int   count=-1;  
  for(int   i=0;i<dataarr.Length;i++)  
  {  
  t=Convert.ToInt32(Math.Round(Convert.ToDouble(count/CacheSize)).ToString());  
  try  
  {//Convert.ToInt32(dataarr[i].Rows[j][0])  
  axZKFPEngX2.AddRegTemplateStrToFPCacheDB(k[t],Convert.ToInt32(dataarr[i].Rows[j][0]),dataarr[i].Rows[j]["FPKey1"].ToString().Trim());  
  }  
  catch(Exception   ee){MessageBox.Show(ee.Message+ee.StackTrace+"\r\n"+dataarr[i].Rows[j][0]+"\r\n"+dataarr[i].Rows[j]["FPKey1"]+"\r\n");};  
  //将数据写入比较缓存  
  }  
  dataarr=null;  
  dte=DateTime.Now;  
  dtC=CandAdditional_FP_C.SelectByWhere("   and   FPKey1<>''",ThreadCount);  
  dtCCount=dtC.Rows.Count;  
  GC.Collect();  
  DateTime   dt3=DateTime.Now;  
  log.Write("----------Step   3:开始指纹比对:"+dte+"\r\n");  
  if(ThreadFlag)//判断是否为多线程  
  {  
  //多线程操作  
  timer1=new   System.Threading.Timer(new   TimerCallback(OnTimer),k,0,1000);  
  }  
  else  
  {  
  //单线程操作  
  }  
  if(ThreadFlag)  
  {  
  ev.WaitOne();  
  }  
  DateTime   dt2=DateTime.Now;  
  log.Write("----------Step   3:结束指纹比对:"+dt2+",共花了:"+new   DateTime(dt2.Ticks-dt3.Ticks).ToString("mm:ss.mmm")+"\r\n");  
  }  
  catch(Exception   ee){MessageBox.Show(ee.Message+ee.StackTrace);if(LogFlag){log.Write("出错:"+ee.Message+"\r\n"+ee.StackTrace);log.Close();}}  
   
  }  
  private   static   void   OnTimer(object   state)  
  {  
  lock(typeof(CompareFingerPrint))  
  {  
  if((CompareFingerPrint.instanceCount<RunCount)&&(startCount<dtCCount))     
             {    
               while(startCount<=dtCCount)    
               {    
  Ergs   s=new   Ergs();  
  s.k=(int[])state;  
  s.dr=dtC.Rows[startCount];  
  s.count=dtC.Rows.Count;  
  s._ev=ev;  
  s.i=startCount;  
  CompareFingerPrint   scanIt1=new   CompareFingerPrint(s.dr,s.i,s.count,s.k,s._ev);  
  scanIt1.DoScan();  
  startCount++;  
  }  
                 if(CompareFingerPrint.instanceCount>=RunCount   ||   startCount+1>=dtCCount)break;  
               }           
             }    
              if(startCount>=dtCCount){CompareFingerPrint.ShouldStop=true;timer1.Dispose();}  
  }  
  public   class   Ergs  
  {  
  public   DataRow   dr;  
  public   int   i;  
  public   int   count;  
  public   int[]   k;  
  public   ManualResetEvent   _ev;  
  }  
  public   class   CompareFingerPrint    
  {        
  private     ManualResetEvent   ev;  
  private     Thread   thread;  
  public       static   int     instanceCount=0;     //同时存在的对象个数  
  public       static   bool   ShouldStop=false;  
  private   int   i;  
  public   string   Can_key;  
  public   string   FPkey1;  
  private   int[]   SelfCacheUsage;  
  public   static   int[]   CacheUsage;  
  int[]   k;  
  int   Score=8;  
  int   ProcessNum=0;  
  int   count;  
  public   CompareFingerPrint(DataRow   dr,int   i,int   count,int[]   k,ManualResetEvent   _ev)  
  {  
  this.Can_key=dr[0].ToString();  
  this.FPkey1=dr["FPKey1"].ToString();  
  this.i=i;  
  this.count=count;  
  this.k=k;  
  CacheUsage=new   int[k.Length];  
  SelfCacheUsage=new   int[k.Length];  
    ev=_ev;  
  thread=new   Thread(new   ThreadStart(target));  
  lock(typeof(CompareFingerPrint)){   instanceCount++;   }   //同时存在的对象个数加一  
  }  
  public   void   DoScan()  
  {      
  thread.Start();  
  }  
  private   void   target()  
  {  
  try  
  {    
  string   temp=FPkey1;//dtC.Rows[i]["FPKey1"].ToString();  
  dts=DateTime.Now;  
  while(DoFinish())  
  {  
  int[]   arr=GetCache();  
  try  
  {  
   
  if(arr[0]!=-1)  
  {  
  ProgressBarForm.log.Write("第"+Convert.ToString(i+1)+"个:"+this.Can_key+"开始第"+arr[0]+"个Cache比对");  
  //进行指纹比对,单线程下比完20000条需要5秒钟左右  
  result=ProgressBarForm.axZKFPEngX2.IdentificationFromStrInFPCacheDB(arr[1],temp,ref   Score,ref   ProcessNum);  
  CacheUsage[arr[0]]=0;  
  SelfCacheUsage[arr[0]]=1;  
  ProgressBarForm.log.Write("第"+Convert.ToString(i+1)+"个:"+this.Can_key+"结束第"+arr[0]+"个Cache比对");  
  }  
  }  
  catch(Exception   ee){MessageBox.Show(ee.Message+ee.StackTrace+"\r\n"+i);CacheUsage[arr[0]]=0;break;};  
  }  
  }  
  catch(Exception   e){MessageBox.Show(e.Message+e.StackTrace);}  
  finally  
  {  
  lock(typeof(CompareFingerPrint))  
  {  
  GC.Collect();  
  if((--instanceCount==0)&&(CompareFingerPrint.ShouldStop))   {ev.Set();ProgressBarForm.canExit=true;}   //同时存在的对象个数减一  
  }  
  }  
  }  
  private   bool   DoFinish()  
  {  
  for(int   i=0;i<SelfCacheUsage.Length;i++)  
  {  
  if(SelfCacheUsage[i]==0)  
  {  
  return   true;  
  }  
  }  
  return   false;  
  }  
  private   int[]   GetCache()  
  {  
  lock(this)  
  {  
  for(int   i=0;i<CacheUsage.Length;i++)  
  {  
  if(CacheUsage[i]==0   &&   SelfCacheUsage[i]==0)  
  {  
  CacheUsage[i]=1;  
  return   new   int[]{i,k[i]};  
  }  
  }  
  return     new   int[]{-1,-1};  
  }  
  }  
  }  
  问题点数:100、回复次数:23Top

1 楼Knight94(愚翁)回复于 2006-08-14 20:51:15 得分 0

代码太长,你说说你的主要流程  
   
  多线程不一定有助于提高效率。Top

2 楼hdt(倦怠)回复于 2006-08-14 20:51:20 得分 0

可以使用异步操作  
  Top

3 楼chrislv(小吕)回复于 2006-08-14 20:56:17 得分 0

从服务器取出20W条数据,放到指纹比对缓存,然后再取出客户端的指纹数据大概1000多条。  
  单线程情况是循环1000次,就是把客户端的一条条数据与缓存比对。一条大概是一分钟。想用多线程节省时间。。。Top

4 楼Knight94(愚翁)回复于 2006-08-14 21:02:39 得分 0

那你首先想想对于一条记录处理,哪些是可以同步操作,哪些是不需要的。Top

5 楼chrislv(小吕)回复于 2006-08-14 22:42:35 得分 0

有没有什么好介绍呀???搞了几天头晕死了。。。。Top

6 楼coolstarhty(语言多了,编程不好学啊)回复于 2006-08-14 22:56:38 得分 10

想用多线程节省时间。。。  
  ----------------------------------------  
   
  使用多线程并不能节省时间,因为CPU最大的工作频率是一定的,  
  使用多线程只是为不同的程序比较合理地安排运行时间,是多个程序看起来是同时运行。  
   
  要想快,要考虑的是如何提高硬件性能,不能无法考虑硬件因素,只能优化程序了。Top

7 楼pyuan(菜鸟)回复于 2006-08-14 23:28:45 得分 0

建义楼主升级电脑。。。。。。Top

8 楼kkbspod(我被可乐淹死了)回复于 2006-08-14 23:30:17 得分 0

多线程是为了高效使用软硬件资源,如果你的这些资源都已经满负荷运转了,再用多线程只会越用越慢Top

9 楼chrislv(小吕)回复于 2006-08-15 10:00:06 得分 0

那本身我写的代码能不能发挥作用,各位帮帮忙Top

10 楼cancerser(都是混饭吃,记得要结帖)回复于 2006-08-15 10:22:19 得分 0

指纹对比   本身就很毫资源的,要真想提高效率就得分布式处理了Top

11 楼thirdman(大肥猪)回复于 2006-08-15 11:31:15 得分 0

是图像比对嘛?你将图像特征数字化了嘛,然后建立快照啊。Top

12 楼chrislv(小吕)回复于 2006-08-15 11:34:44 得分 0

是字符串的,指纹控件提供了方法对比的。Top

13 楼ProjectDD()回复于 2006-08-15 11:41:56 得分 10

按MSDN标准文档的说法多线程可能   会因为线程过多,或其它方面的复杂原因而“降低”运行效率,多线程增加了,线程协调,和管理方面的成本,当线程过多时会极大的加重运行和资源方面的“成本”而且可能会发生复杂问题,大概   多线程更适合于同时完成多个任务,而不是增益运行效率,效率方面仅主要信赖于硬件,配置方面。Top

14 楼chrislv(小吕)回复于 2006-08-15 15:38:04 得分 0

不知道还有没有其它的解决方案???各位大虾帮帮我呀Top

15 楼Knight94(愚翁)回复于 2006-08-15 15:43:53 得分 30

to   不知道还有没有其它的解决方案???  
   
  其实大家已经说得很清楚了。  
   
  你首先要分析你现在处理的瓶颈在哪儿,而这个瓶颈是否能通过多线程来改善。Top

16 楼chrislv(小吕)回复于 2006-08-15 15:45:06 得分 0

谢谢各位。Top

17 楼chrislv(小吕)回复于 2006-08-15 15:51:08 得分 0

to   hdt(倦怠)   可以使用异步操作  
  如何操作?可否告之。。。Top

18 楼softbunny(软件兔)回复于 2006-08-15 16:08:48 得分 20

如果你比对一个指纹时是一直在计算的话,那线程越多速度越慢.  
   
  例外情况是你的服务器有多个CPU,那才能真正发挥多线程的优势,有多少个CPU就开多少线程.Top

19 楼chenyinxin(这里我最菜)回复于 2006-08-15 16:17:03 得分 0

是字符串的,指纹控件提供了方法对比的。  
   
  --------------  
  查看CPU和内存使用情况,如果用尽了,那只能升硬件  
  是否控件本身性能有问题?  
  最好能把数据都加载到内存!Top

20 楼dahaig(HarryPottor)回复于 2006-08-15 16:23:02 得分 10

多线程在单cpu机器上不能提高cpu效率,除非你是多cpu的机器  
  多线程才能发挥效果  
  解决办法,  
  建议将指纹数据压缩,到服务器再解压缩  
  Top

21 楼scow(怡红快绿之小橙子|和谐权是第4代人权)回复于 2006-08-15 16:35:28 得分 10

多线程带来的调度开销和速度方面能够提高的,哪个起主导作用,还是测试才知道,既然比单线程还慢,看来还是前者起了主导作用,不知改一下这个多线程的实现行不行,高手来解释解释Top

22 楼xiaolonghong()回复于 2006-08-15 20:56:02 得分 10

多线程的目标是充分利用硬件资源,如果cpu在运行时达到100%了,那再多线程不但没用,反而使运行更慢....  
  Top

23 楼myminimouse(坚决不用baidu)回复于 2006-08-15 21:25:34 得分 0

upTop

相关问题

关键词

得分解答快速导航

  • 帖主:chrislv
  • coolstarhty
  • ProjectDD
  • Knight94
  • softbunny
  • dahaig
  • scow
  • xiaolonghong

相关链接

  • CSDN .NET频道
  • .NET类图书
  • C#类图书
  • .NET类源码下载

广告也精彩

反馈

请通过下述方式给我们反馈
反馈
提问
网站简介|广告服务|VIP资费标准|银行汇款帐号|网站地图|帮助|联系方式|诚聘英才|English|问题报告
北京创新乐知广告有限公司 版权所有, 京 ICP 证 070598 号
世纪乐知(北京)网络技术有限公司 提供技术支持
Copyright © 2000-2008, CSDN.NET, All Rights Reserved
GongshangLogo