iOS多线程-常用的线程锁

在高并行的代码环境中,我们常常会碰到这样的情况:多个线程同时访问某一段代码,产生资源竞争,导致程序异常。线程锁可以帮我们解决这样的问题,它可以让这些并行的线程同步地访问这段代码,让我们的程序正常执行。通过解决下面这个问题(参见 http://www.jianshu.com/p/b3bd070cd372 ),介绍几种常用线程锁的用法。

- (void)testDispatchSemaphore
{
    dispatch_queue_t queue = dispatch_get_global_queue(DISPATCH_QUEUE_PRIORITY_DEFAULT, 0);

    NSMutableArray *mutableArray = [NSMutableArray array];

    for (int i = 0; i < 100000; ++i) {
        dispatch_async(queue, ^{
            [mutableArray addObject:[NSNumber numberWithInt:i]];
        });
    }
}

一、NSLock

    NSLock *lock = [[NSLock alloc] init];
    
    for (int i = 0; i < 100000; ++i) {
        dispatch_async(queue, ^{
            //加锁
            [lock lock];
            //需要加锁的代码
            [mutableArray addObject:[NSNumber numberWithInt:i]];
            //解锁
            [lock unlock];
        });
    }

三步:

  1. 初始化锁:
NSLock *lock = [[NSLock alloc] init];
  1. 对代码加锁:
 [lock lock];
  1. 对代码解锁:
[lock unlock];

二、pthread_mutex

    static pthread_mutex_t pLock;
    pthread_mutex_init(&pLock, NULL);
    
    for (int i = 0; i < 100000; ++i) {
        dispatch_async(queue, ^{
            //加锁
            pthread_mutex_lock(&pLock);
            //需要加锁的代码
            [mutableArray addObject:[NSNumber numberWithInt:i]];
            //解锁
            pthread_mutex_unlock(&pLock);
        });
    }

四步:

  1. 声明:
static pthread_mutex_t pLock;

这里需要声明为静态变量,不然参数类型不匹配。

  1. 初始化:
pthread_mutex_init(&pLock, NULL);
  1. 加锁
pthread_mutex_lock(&pLock);
  1. 解锁
pthread_mutex_unlock(&pLock);

三、@synchronized

    for (int i = 0; i < 100000; ++i) {
        dispatch_async(queue, ^{
            @synchronized (self) {
                [mutableArray addObject:[NSNumber numberWithInt:i]];
            }
        });
    }

最简单,但是性能最差

四、Dispatch Semaphore

我写的另一篇文章有分析到,详情见http://www.jianshu.com/p/b3bd070cd372

综合性能和可读性,我比较喜欢NSLock,对性能要求较高的童鞋可以使用pthread_mutex_t和Semaphore。自旋锁OSSpinLock被苹果工程师证实不安全,苹果使用pthread_mutex_t进行了替代,谷歌使用Semaphore。

你可能感兴趣的:(iOS多线程-常用的线程锁)