文章轉(zhuǎn)自https://www.cnblogs.com/yajunLi/p/6274282.html
理解這個(gè)概念之前掖鱼,先拋出一個(gè)問(wèn)題
問(wèn)題描述:
假設(shè)現(xiàn)在系統(tǒng)有兩個(gè)空閑資源可以被利用,但同一時(shí)間卻有三個(gè)線程要進(jìn)行訪問(wèn)唆迁,這種情況下芹扭,該如何處理呢篮撑?
或者
我們要下載很多圖片纹安,并發(fā)異步進(jìn)行毛俏,每個(gè)下載都會(huì)開(kāi)辟一個(gè)新線程,可是我們又擔(dān)心太多線程肯定cpu吃不消杏死,那么我們這里也可以用信號(hào)量控制一下最大開(kāi)辟線程數(shù)。
定義:
1捆交、信號(hào)量:就是一種可用來(lái)控制訪問(wèn)資源的數(shù)量的標(biāo)識(shí)淑翼,設(shè)定了一個(gè)信號(hào)量,在線程訪問(wèn)之前品追,加上信號(hào)量的處理玄括,則可告知系統(tǒng)按照我們指定的信號(hào)量數(shù)量來(lái)執(zhí)行多個(gè)線程。
其實(shí)肉瓦,這有點(diǎn)類似鎖機(jī)制了遭京,只不過(guò)信號(hào)量都是系統(tǒng)幫助我們處理了,我們只需要在執(zhí)行線程之前泞莉,設(shè)定一個(gè)信號(hào)量值哪雕,并且在使用時(shí),加上信號(hào)量處理方法就行了鲫趁。
2斯嚎、信號(hào)量主要有3個(gè)函數(shù),分別是:
//創(chuàng)建信號(hào)量挨厚,參數(shù):信號(hào)量的初值堡僻,如果小于0則會(huì)返回NULL
dispatch_semaphore_create(信號(hào)量值)
//等待降低信號(hào)量
dispatch_semaphore_wait(信號(hào)量,等待時(shí)間)
//提高信號(hào)量
dispatch_semaphore_signal(信號(hào)量)
注意疫剃,正常的使用順序是先降低然后再提高钉疫,這兩個(gè)函數(shù)通常成對(duì)使用〕布郏∩蟆(具體可參考下面的代碼示例)
3、那么就開(kāi)頭提的問(wèn)題蹄溉,我們用代碼來(lái)解決
-(void)dispatchSignal{
????//crate的value表示咨油,最多幾個(gè)資源可訪問(wèn)
????dispatch_semaphore_t semaphore = dispatch_semaphore_create(2);???
????dispatch_queue_t quene = dispatch_get_global_queue(DISPATCH_QUEUE_PRIORITY_DEFAULT, 0);
????//任務(wù)1
????dispatch_async(quene, ^{
????????dispatch_semaphore_wait(semaphore, DISPATCH_TIME_FOREVER);
????????NSLog(@"run task 1");
????????sleep(1);
????????NSLog(@"complete task 1");
????????dispatch_semaphore_signal(semaphore);???????
????});
????//任務(wù)2
????dispatch_async(quene, ^{
????????dispatch_semaphore_wait(semaphore, DISPATCH_TIME_FOREVER);
????????NSLog(@"run task 2");
????????sleep(1);
????????NSLog(@"complete task 2");
????????dispatch_semaphore_signal(semaphore);???????
????});
????//任務(wù)3
????dispatch_async(quene, ^{
????????dispatch_semaphore_wait(semaphore, DISPATCH_TIME_FOREVER);
????????NSLog(@"run task 3");
????????sleep(1);
????????NSLog(@"complete task 3");
????????dispatch_semaphore_signal(semaphore);???????
????});???
}
執(zhí)行結(jié)果:
總結(jié):由于設(shè)定的信號(hào)值為2,先執(zhí)行兩個(gè)線程柒爵,等執(zhí)行完一個(gè)役电,才會(huì)繼續(xù)執(zhí)行下一個(gè),保證同一時(shí)間執(zhí)行的線程數(shù)不超過(guò)2棉胀。
這里我們擴(kuò)展一下法瑟,假設(shè)我們?cè)O(shè)定信號(hào)值=1
1dispatch_semaphore_create(1)
那么結(jié)果就是:
如果設(shè)定信號(hào)值=3
1dispatch_semaphore_create(3)
那么結(jié)果就是:?
其實(shí)設(shè)定為3冀膝,就是不限制線程執(zhí)行了,因?yàn)橐还膊胖挥?個(gè)線程霎挟。