互斥量 (Mutex)
在计算机科学中,锁是在执行多线程时用于强行限制资源访问的同步机制。
在iOS中,实现互斥量有多种方式,一般有
- @synchronized 同步代码快
@synchronized(self) {
// task
}
- NSLock 对象锁
NSLock *mutexLock = [[NSLock alloc] init];
[mutexLock lock];
//task
[mutexLock unlock];
-
NSRecursiveLock 递归锁
NSLock在递归中容易产生死锁,使用NSRecursiveLock可以避免这个问题 -
NSConditionLock 条件锁
满足预设的条件,就可以获取锁 -
OSSpinLock 自旋锁
一般的互斥锁没有拿到锁之前,线程都会休眠,而自旋锁不会引起调用者线程休眠,调用者就一直循环在那里看是否该自旋锁的保持者已经释放了锁。 -
pthread_mutex C语言实现的互斥锁
信号量(Semaphore)
信号量是一个同步对象,用于保持在0至指定最大值之间的一个计数值。当线程完成一次对该semaphore对象的等待(wait)时,该计数值(- 1);当线程完成一次对semaphore对象的释放(release)时,计数值(+ 1)。简单来说,信号量为0的时候,线程会阻塞,一直等待该信号量对象的计数值变成大于0的状态。
dispatch_queue_t queue =
dispatch_get_global_queue(DISPATCH_QUEUE_PRIORITY_DEFAULT, 0);
dispatch_semaphore_t semaphore = dispatch_semaphore_create(0);//信号量初始为0
dispatch_async(queue, ^{
// task1
dispatch_semaphore_signal(semaphore);// 使信号量+1并返回
});
dispatch_semaphore_wait(semaphore, DISPATCH_TIME_FOREVER);
// task2
//只有当task1执行完,信号量+1之后,才会执行这里
数值为N的信号量允许N个线程并发访问。
如果信号量是一个任意的整数,通常被称为计数信号量(Counting semaphore),或一般信号量(general semaphore);如果信号量只有二进制的0或1,称为二进制信号量(binary semaphore)。在linux系统中,二进制信号量(binary semaphore)又称互斥量(Mutex)。
所以说,互斥量和信号量本质上一样,都是用来表示对资源的访问权,但是互斥量表示资源某个时刻最多只能被一个线程占用,也就是资源计数最多是1,而信号量的资源计数可以超过1,即同时被多个线程占用。
两者对比的话,简单来说,
- 互斥量就是N个线程,争夺一把锁,
- 信号量就是N个线程,争夺M把锁,当信号量的计数值只有0、1(二进制信号量),那么M = 1,这时候,和互斥量的性质是一样的。
网友评论