上司交代要做一個(gè)小測試
具體的需求是 在某一時(shí)間點(diǎn),只有n個(gè)線程在并發(fā)執(zhí)行,如果有多余的線程,則排隊(duì)等候~
還真是費(fèi)盡心思啊~最終還是被我攻克了~
下面我就來說說具體的實(shí)現(xiàn)
c#提供了mutex與interlocked這兩個(gè)與線程相關(guān)的類,都在threading命名空間下~!
mutex中提供了witeone,releasemutex 兩個(gè)實(shí)例方法~
witeone的作用是"阻塞當(dāng)前線程,提供對該線程的原子操作"
也就是說當(dāng)一個(gè)線程遇到witeone的時(shí)候,如果在witeone里面沒有線程在操作,則此線程進(jìn)去操作
而里面有線程的時(shí)候,所有到此的線程均需要排隊(duì)等候里面的線程執(zhí)行完畢~
而控制這樣操作的結(jié)束標(biāo)記就是使用releasemutex 方法!
就好比witeone是一把鎖一樣~而releasemutex 就是一把鑰匙
當(dāng)10個(gè)人都看到這個(gè)門的時(shí)候,第一個(gè)到達(dá)門口的人會看到屋子里沒有人,則他進(jìn)去,同時(shí)會把門鎖上~
后面的人自然要在門口等候,當(dāng)此人在屋子里執(zhí)行完任務(wù)后他會用鑰匙把門打開!
出去后把鎖交給門口排隊(duì)的第二位同志,第二位同志再做同樣的操作
如果第一位同志執(zhí)行完任務(wù)以后不把使用權(quán)交給第二個(gè)人的話,而直接退出
那么屋子自然就空了下來,而門還是鎖的~不必?fù)?dān)心~門會自動(dòng)打開,只要是前一個(gè)人已經(jīng)不在屋子里即可~
然后再來說說這個(gè)interlocked,官方說明是"對一個(gè)變量進(jìn)行原子操作進(jìn)行遞增或者遞減然后保存"
原子操作的概念就是,有且只有一個(gè)線程在對此變量進(jìn)行操作~不準(zhǔn)其他線程干預(yù)的操作
當(dāng)對一個(gè)變量進(jìn)行原子操作的時(shí)候,此變量就會加鎖,而其他線程是無法訪問的,只能掛起等候此變量解鎖
我感覺實(shí)際上使用的也就是mutex來實(shí)現(xiàn)的
好了開始說說具體的實(shí)現(xiàn)吧
public class mutextest
 {
  private static int poolflag = 0 ;//標(biāo)記
  private const int amountthread = 10 ;//線程總量
  private const int maxthread = 3 ;//可執(zhí)行線程最大數(shù)量
  private static mutex muxconsole = new mutex() ;
  
  public static void main()
  {
   for ( int i = 0 ; i < amountthread ; i ++ )
   {
    // 創(chuàng)建指定數(shù)量的線程
    // 是線程調(diào)用run方法
    // 啟動(dòng)線程
    thread trd = new thread( new threadstart( run ) ) ;
    trd.name = "線程" + i ;
    trd.start() ;
   }
  }
  public static void run()
  {                                                                                                                                                                                                                                         
   muxconsole.waitone();  //阻塞隊(duì)列
   interlocked.increment(ref poolflag) ;  //標(biāo)記+1
   if (poolflag != maxthread)             //判斷是否等于上限
    muxconsole.releasemutex();     //如果此線程達(dá)不到可執(zhí)行線程上限,則繼續(xù)開通,讓后面的線程進(jìn)來
   console.writeline( "{0} 正在運(yùn)行....../n", thread.currentthread.name ) ;
   thread.sleep( 5000 );                                                                                             //模擬執(zhí)行
   console.writeline( "{0} 已經(jīng)中止....../n", thread.currentthread.name ) ;
   //標(biāo)記-1
   interlocked.decrement(ref poolflag) ; 
  }
 }
注釋很全,大家慢慢看吧~我準(zhǔn)備把這個(gè)用到webservice的負(fù)載平衡上面~
這樣我就可以自己控制請求的數(shù)量了~
新聞熱點(diǎn)
疑難解答
圖片精選