dispatch_semaphore_create(1)
创建一个 semaphore
信号总量为 1
dispatch_semaphore_wait(lock, DISPATCH_TIME_FOREVER)
如果信号总量为0,进入等待状态,信号量大于0时,继续执行代码,同时将信号总量 -1
dispatch_semaphore_signal(lock);
发送信号量,信号量 +1
使用时注意使用
signal
以确保编译器release
掉dispatch_semaphore_t
时的值与初始值一致, 否则会EXC_BAD_INSTRUCTION
,见http://is.gd/EaJgk5
dispatch_semaphore_t lock = dispatch_semaphore_create(1);
for (int i = 0; i < 10; i++)
{
dispatch_semaphore_wait(lock, DISPATCH_TIME_FOREVER);
dispatch_async(dispatch_get_global_queue(0, 0), ^{
NSLog(@"%d", i);
dispatch_semaphore_signal(lock);
});
}
获取通讯录
dispatch_semaphore_t sema = dispatch_semaphore_create(0);
ABAddressBookRequestAccessWithCompletion(abRef, ^(bool granted, CFErrorRef error)
{
isOpen = granted;
dispatch_semaphore_signal(sema);
});
dispatch_semaphore_wait(sema, DISPATCH_TIME_FOREVER);
CFRelease(abRef);
�
使用 Dispatch Semaphore 控制并发线程数量
void dispatch_async_limit(dispatch_queue_t queue,NSUInteger limitSemaphoreCount, dispatch_block_t block) {
//控制并发数的信号量
static dispatch_semaphore_t limitSemaphore;
//专门控制并发等待的线程
static dispatch_queue_t receiverQueue;
//使用 dispatch_once而非 lazy 模式,防止可能的多线程抢占问题
static dispatch_once_t onceToken;
dispatch_once(&onceToken, ^{
limitSemaphore = dispatch_semaphore_create(limitSemaphoreCount);
receiverQueue = dispatch_queue_create("receiver", DISPATCH_QUEUE_SERIAL);
});
// 如不加 receiverQueue 放在主线程会阻塞主线程
dispatch_async(receiverQueue, ^{
//可用信号量后才能继续,否则等待
dispatch_semaphore_wait(limitSemaphore, DISPATCH_TIME_FOREVER);
dispatch_async(queue, ^{
!block ? : block();
//在该工作线程执行完成后释放信号量
dispatch_semaphore_signal(limitSemaphore);
});
});
}
������
�������������