用法:
- (void)viewDidLoad {
[super viewDidLoad];
[self nsconditionlock];
}
- (void)nsconditionlock {
NSConditionLock * cjlock = [[NSConditionLock alloc] initWithCondition:0];
dispatch_async(dispatch_get_global_queue(DISPATCH_QUEUE_PRIORITY_DEFAULT, 0), ^{
[cjlock lock];
NSLog(@"线程1加锁成功");
sleep(1);
[cjlock unlock];
NSLog(@"线程1解锁成功");
});
dispatch_async(dispatch_get_global_queue(DISPATCH_QUEUE_PRIORITY_DEFAULT, 0), ^{
sleep(1);
[cjlock lockWhenCondition:1];
NSLog(@"线程2加锁成功");
[cjlock unlock];
NSLog(@"线程2解锁成功");
});
dispatch_async(dispatch_get_global_queue(DISPATCH_QUEUE_PRIORITY_DEFAULT, 0), ^{
sleep(2);
if ([cjlock tryLockWhenCondition:0]) {
NSLog(@"线程3加锁成功");
sleep(2);
[cjlock unlockWithCondition:2];
NSLog(@"线程3解锁成功");
} else {
NSLog(@"线程3尝试加锁失败");
}
});
dispatch_async(dispatch_get_global_queue(DISPATCH_QUEUE_PRIORITY_DEFAULT, 0), ^{
if ([cjlock lockWhenCondition:2 beforeDate:[NSDate dateWithTimeIntervalSinceNow:10]]) {
NSLog(@"线程4加锁成功");
[cjlock unlockWithCondition:1];
NSLog(@"线程4解锁成功");
} else {
NSLog(@"线程4尝试加锁失败");
}
});
}
控制台输出:
2017-10-19 15:09:44.010992+0800 Thread-Lock[39230:853946] 线程1加锁成功
2017-10-19 15:09:45.012045+0800 Thread-Lock[39230:853946] 线程1解锁成功
2017-10-19 15:09:46.012692+0800 Thread-Lock[39230:853947] 线程3加锁成功
2017-10-19 15:09:48.016536+0800 Thread-Lock[39230:853947] 线程3解锁成功
2017-10-19 15:09:48.016564+0800 Thread-Lock[39230:853944] 线程4加锁成功
2017-10-19 15:09:48.017039+0800 Thread-Lock[39230:853944] 线程4解锁成功
2017-10-19 15:09:48.017040+0800 Thread-Lock[39230:853945] 线程2加锁成功
2017-10-19 15:09:48.017215+0800 Thread-Lock[39230:853945] 线程2解锁成功
由以上内容总结:
-
在线程 1 解锁成功之后,线程 2 并没有加锁成功,而是继续等了 1 秒之后线程 3 加锁成功,这是因为线程 2 的加锁条件不满足,初始化时候的 condition 参数为 0,而线程 2
加锁条件是 condition 为 1,所以线程 2 加锁失败。
lockWhenCondition 与 lock 方法类似,加锁失败会阻塞线程,所以线程 2 会被阻塞着。
tryLockWhenCondition: 方法就算条件不满足,也会返回 NO,不会阻塞当前线程。
lockWhenCondition:beforeDate:方法会在约定的时间内一直等待 condition 变为 2,并阻塞当前线程,直到超时后返回 NO。
锁定和解锁的调用可以随意组合,也就是说 lock、lockWhenCondition:与unlock、unlockWithCondition: 是可以按照自己的需求随意组合的。










