一 gcd死锁条件,
1 资源被限制1个进程使用(互斥条件);
2 一个进程请求资源后阻塞,仍然保持不放(请求与保持条件);
3 进程资源也不被强行剥夺(不剥夺条件);
4 进程间造成循环等待资源的情况(循环等待条件);
说明:进程之间的资源竞争造成,任何一个条件不成立都不会死锁。
二 死锁结构?
dispatch_x(q,^{
dispatch_sync(q,^{});
});
*内外q都是同一个q,且q是串行队列(main queue或者create的serial queue)
* 内层dispatch是同步;
*外层dispatch可以是同步,也可以是异步;
死锁解决:异步dispatch;
三 死锁3个例子
例1:
dispatch_sync(_mainQueue, ^{ });//同步调用,_mainQueue:因为block内任务会被加到主队列尾部,死锁;
[self doSometing:@"1"];
dispatch_sync(_mainQueue, ^{
[self doSometing:@"2"];
});
[self doSometing:@"3"];
输出:1 ;
说明:因为_mainQueue主队列,会将任务2加到队尾,遵循FIFO原则执行任务。所以任务2和任务3相互等待,产生死锁;
备注:此例可以看成外层queue是_mainQueue,这样与死锁结构对应。
例2:
dispatch_async(_mainQueue, ^{
[self doSometing:@"1"];
dispatch_sync(self->_mainQueue, ^{
[self doSometing:@"2"];
});
});
[self doSometing:@"3"];
输出:3 1 ;然后死锁;
例3:自定义串行队列
dispatch_queue_t serialQueue = dispatch_queue_create("myQueue", DISPATCH_QUEUE_SERIAL);
dispatch_async(serialQueue, ^{
[self doSometing:@"1"];
dispatch_sync(serialQueue, ^{
[self doSometing:@"2"];
});
});
[self doSometing:@"3"];
输出:1 3;然后死锁