参考文章在GCD中,我们通常使用dispatch_semaphore来处理并发控制,
semaphore主要有三个函数操作分别是:
<pre><code>
dispatch_semaphore_create //创建semaphore,此时可以传入一个初始的信号量值
</pre></code>
<pre><code>
dispatch_semaphore_signal //发送一个信号,当信号量被发送后,semaphore中的计数会加1
</pre></code>
<pre><code>
dispatch_semaphore_wait // 等待信号,会使semaphore的计数减1,当semaphore中的计数小于0时,线程会被阻塞,直至计数大于0
</pre></code>
总结就是dispatch_semaphore_signal发送一个信号,使得信号总量加1,dispatch_semaphore_wait等待信号,当信号总量小于0时会一直等待,否则可以正常运行并让信号量减1,
<code><pre>
dispatch_group_t group = dispatch_group_create();
dispatch_semaphore_t semaphore = dispatch_semaphore_create(10);
dispatch_queue_t queue = dispatch_get_global_queue(DISPATCH_QUEUE_PRIORITY_DEFAULT,0);
for(in i = 0; i < 100; i++) {
dispatch_semaphore_wait(semaphore,DISPATCH_TIME_FOREVER);
dispatch_group_async(group,queue,^{
NSLog(@"%i",i);
sleep(2);
dispatch_semaphore_signal(semaphore);
});
}
dispatch_group_wait(group,DISPATCH_TIME_FOREVER);
</pre></code>
当初始化时设置信号量为1时就可以当做资源锁来使用.在没有等待情况出现时,其性能比OSSpinLock自旋锁还要高。但是一旦有等待情况出现时,其性能会下降很多。
<code><pre>
+ (nullable instancetype)classInfoWithClass:(Class)cls {
//1.类缓存
static CFMutableDictionaryRef classCache;
//2.资源锁
static dispatch_semaphore_t lock;
//3.创建单例
static dispatch_once_t onceToken;
dispatch_once(&onceToken, ^{
classCache = CFDictionaryCreateMutable(CFAllocatorGetDefault(), 0, &kCFTypeDictionaryKeyCallBacks, &kCFTypeDictionaryValueCallBacks);
lock = dispatch_semaphore_create(1);
});
//4.加锁并取出缓存的类信息
dispatch_semaphore_wait(lock, DISPATCH_TIME_FOREVER);
XRClassInfo *info = CFDictionaryGetValue(classCache, (__bridge const void *)(cls));
dispatch_semaphore_signal(lock);
//5.如果没有缓存的类信息,则需要重新创建,并缓存
if(!info) {
//6.根据类,创建新的类信息
info = [[XRClassInfo alloc] initWithClass:cls];
if(info) {
dispatch_semaphore_wait(lock, DISPATCH_TIME_FOREVER);
CFDictionarySetValue(classCache, (__bridge const void *)(cls), (__bridge const void *)(info));
dispatch_semaphore_signal(lock);
}
}
return info;
}
</pre></code>
欢迎大家关注我的微信公众号
网友评论