dispatch_semaphore是GCD中的信號量纤虽,可以處理多線程中線程并發(fā)的問題狡刘,也可以用作同步處理
一襟诸、dispatch_semaphore方法
創(chuàng)建信號量瓦堵,里面的參數(shù)是表示信號的總量,值必須>=0
dispatch_semaphore_t semaphore = dispatch_semaphore_create(0);
發(fā)送一個信號歌亲,信號量的總數(shù)會+1
dispatch_semaphore_signal(semaphore);
信號等待菇用,當(dāng)信號量的總數(shù)<=0的時候,會一直等待陷揪,直到信號量的總數(shù)>0的時候才會繼續(xù)下面的執(zhí)行
dispatch_semaphore_wait(semaphore, DISPATCH_TIME_FOREVER);
注意:dispatch_semaphore_wait
當(dāng)信號量的總數(shù)<=0時候惋鸥,該函數(shù)所在的線程就會等待,而信號量的總數(shù)>0的時候悍缠,該函數(shù)就會繼續(xù)往下執(zhí)行卦绣,同時信號量的總數(shù)-1
這里有個等待時間的參數(shù),如果在等待的時間內(nèi)獲得了信號量飞蚓,那么函數(shù)繼續(xù)往下執(zhí)行滤港,如果等待時間內(nèi)信號量一直為0,那么函數(shù)也會繼續(xù)往下執(zhí)行了
二趴拧、代碼
實例一:信號量基本用法
- (void)test2 {
//信號量
//創(chuàng)建總數(shù)為10的信號量
dispatch_semaphore_t semaphore = dispatch_semaphore_create(10);
dispatch_queue_t queue = dispatch_get_global_queue(DISPATCH_QUEUE_PRIORITY_DEFAULT, 0);
for (int i = 0; i < 100; i++) {
//這里注意當(dāng)?shù)却龝r間為10和1的線程的區(qū)別
dispatch_time_t time = dispatch_time(DISPATCH_TIME_NOW, 10);
//信號量總數(shù)>0溅漾,繼續(xù)執(zhí)行,否則等待
dispatch_semaphore_wait(semaphore, time);
dispatch_async(queue, ^{
NSLog(@"%i~~~~~%@",i, [NSThread currentThread]);
sleep(3);
//發(fā)送信號八堡,信號量總數(shù)+1
dispatch_semaphore_signal(semaphore);
});
}
}
實例二:使用NSURLSession同步請求(使用信號量)
- (void)test3 {
NSMutableURLRequest *request = [[NSMutableURLRequest alloc]initWithURL:[NSURL URLWithString:@"http://imgsrc.baidu.com/forum/w%3D580/sign=16ccb289970a304e5222a0f2e1caa7c3/4ee3cc5c10385343102141ac9313b07ec880889f.jpg"] cachePolicy:NSURLRequestUseProtocolCachePolicy timeoutInterval:30];
dispatch_semaphore_t semaphore = dispatch_semaphore_create(0);
NSURLSessionTask *dataTask = [[NSURLSession sharedSession] dataTaskWithRequest:request completionHandler:^(NSData * _Nullable data, NSURLResponse * _Nullable response, NSError * _Nullable error) {
NSLog(@"~~~~~~下載完成了呢");
//發(fā)送信號
dispatch_semaphore_signal(semaphore);
}];
[dataTask resume];
dispatch_semaphore_wait(semaphore, DISPATCH_TIME_FOREVER);
NSLog(@"~~~~~~哈哈哈任務(wù)結(jié)束了呢");
}
實例三:使用NSURLSession同步請求(使用group)
- (void)test4 {
NSMutableURLRequest *request = [[NSMutableURLRequest alloc]initWithURL:[NSURL URLWithString:@"http://imgsrc.baidu.com/forum/w%3D580/sign=16ccb289970a304e5222a0f2e1caa7c3/4ee3cc5c10385343102141ac9313b07ec880889f.jpg"] cachePolicy:NSURLRequestUseProtocolCachePolicy timeoutInterval:30];
dispatch_group_t group = dispatch_group_create();
dispatch_queue_t queue = dispatch_queue_create("queue", DISPATCH_QUEUE_CONCURRENT);
//進(jìn)入組
dispatch_group_enter(group);
dispatch_group_async(group, queue, ^{
NSURLSessionTask *dataTask = [[NSURLSession sharedSession] dataTaskWithRequest:request completionHandler:^(NSData * _Nullable data, NSURLResponse * _Nullable response, NSError * _Nullable error) {
NSLog(@"~~~~~~下載完成了呢");
//離開組
dispatch_group_leave(group);
}];
[dataTask resume];
});
//等待組內(nèi)的任務(wù)完成
dispatch_group_wait(group, DISPATCH_TIME_FOREVER);
NSLog(@"~~~~~~哈哈哈任務(wù)結(jié)束了呢");
}