美文网首页
GCD死锁案例解析

GCD死锁案例解析

作者: 开发者老岳 | 来源:发表于2017-07-27 16:25 被阅读36次

参考:http://ios.jobbole.com/82622/

案例一

NSLog(@"1"); // 任务1
dispatch_sync(dispatch_get_main_queue(), ^{
    NSLog(@"2"); // 任务2
});
NSLog(@"3"); // 任务3

//打印结果:
1

分析:dispatch_sync 执行后,会同步任务(即先阻塞当前线程,优先在任务1所在线程执行当前的任务,而把任务2插入到main_queue尾部),所以任务2执行完了才会执行任务3。而任务2是针对main_queue的,只有等main_queue都执行完了才会执行任务2,而main_queue是串行队列,所以只有任务3完成后才会执行任务2。双方同时进入等待状态,造成死锁。

案例二

NSLog(@"1"); // 任务1
dispatch_sync(dispatch_get_global_queue(DISPATCH_QUEUE_PRIORITY_HIGH, 0), ^{
    NSLog(@"2"); // 任务2
});
NSLog(@"3"); // 任务3

//打印结果:
1
2
3

分析:任务2在会在主线程优先执行任务2,故任务2执行完了才会执行任务3。同时任务2是插入到global队列尾部。所以理所当然的,先执行了2,再执行3。

案例三

dispatch_queue_t queue = dispatch_queue_create("com.demo.serialQueue", DISPATCH_QUEUE_SERIAL);
NSLog(@"1"); // 任务1
dispatch_async(queue, ^{
    NSLog(@"2"); // 任务2
    dispatch_sync(queue, ^{  
        NSLog(@"3"); // 任务3
    });
    NSLog(@"4"); // 任务4
});
NSLog(@"5"); // 任务5

//打印结果:
1
5
2
// 5和2的顺序不一定

分析:这个案例没有使用系统提供的串行或并行队列,而是自己通过dispatch_queue_create函数创建了一个DISPATCH_QUEUE_SERIAL的串行队列。
执行任务1;

  • 遇到异步线程,将【任务2、同步线程、任务4】加入串行队列中。因为是异步线程,所以在主线程中的任务5不必等待异步线程中的所有任务完成;
  • 因为任务5不必等待,所以2和5的输出顺序不能确定;
  • 任务2执行完以后,遇到同步线程,这时,将任务3加入串行队列;
  • 又因为任务4比任务3早加入串行队列,所以,任务3要等待任务4完成以后,才能执行。但是任务3所在的同步线程会阻塞,所以任务4必须等任务3执行完以后再执行。这就又陷入了无限的等待中,造成死锁。

案例四

NSLog(@"1"); // 任务1
dispatch_async(dispatch_get_global_queue(0, 0), ^{
    NSLog(@"2"); // 任务2
    dispatch_sync(dispatch_get_main_queue(), ^{
        NSLog(@"3"); // 任务3
    });
    NSLog(@"4"); // 任务4
});
NSLog(@"5"); // 任务5
//打印结果:
1
2
5
3
4
// 5和2的顺序不一定

分析:
1.执行任务1。
2.多线程执行任务2,主线程执行任务5,前后可能随机。
3.任务3执行的时候,因为是同步,所以会先阻塞global线程,然后把任务3插入到主线程后面,等待主线程执行完了,再执行任务3。
4.任务3执行完,任务4所在的global线程阻塞结束,所以最后执行任务4。

如果在任务5前面加一个,sleep(3); 那么结果依然是这个。任务3会一直等待任务5,任务4也会一直等待任务3。

案例五

dispatch_async(dispatch_get_global_queue(0, 0), ^{
    NSLog(@"1"); // 任务1
    dispatch_sync(dispatch_get_main_queue(), ^{
        NSLog(@"2"); // 任务2
    });
    NSLog(@"3"); // 任务3
});
NSLog(@"4"); // 任务4
while (1) {
}
NSLog(@"5"); // 任务5
打印结果:
1
4
// 1、4顺序不一定

分析略,见案例四分析。

相关文章

  • GCD死锁案例解析

    参考:http://ios.jobbole.com/82622/ 案例一 分析:dispatch_sync 执行后...

  • GCD死锁

    GCD死锁的5种案例测试来源: https://my.oschina.net/doxing/blog/618132

  • GCD 死锁 案例 分析

    作者: brighttj(@saitjr题目: 五个案例让你明白GCD死锁网址:http://www.brigh...

  • GCD 死锁案例分析

    案例一:主队列,同步线程 任务1执行后,同步线程任务2加到主队列中,任务3会等待任务2执行完成后执行 对于队列,有...

  • GCD 细细的读

    目录 前言 为什么选择GCD? 串行队列、并行队列、同步、异步 线程死锁解析 DispatchQueue的使用 D...

  • GCD让我死锁的死锁(Two)

    本文目录: 同步执行主队列(在主线程中) 另几种死锁情况 本文参考文章链接: 理解GCD死锁 五个案例让你明白GC...

  • 说说GCD中的死锁

    本文主要举例说明GCD里的死锁场景,分析造成死锁的原因以及解决方案 在开始说GCD死锁之前,我们先了解一下GCD的...

  • 552,GCD的死锁(面试点:gcd死锁:一,主线程调用主线程。

    本文主要举例说明GCD里的死锁场景,分析造成死锁的原因以及解决方案 在开始说GCD死锁之前,我们先了解一下GCD的...

  • iOS——GCD的死锁案例

    在项目中,用GCD的时候非常多,但是我最近脑子里一直在问自己一个问题,死锁是什么。惭愧的是这个当初清晰的概念现在愈...

  • iOS-知识点

    五个案例让你明白GCD死锁:http://ios.jobbole.com/82622/ iOS开发中多线程间关于锁...

网友评论

      本文标题:GCD死锁案例解析

      本文链接:https://www.haomeiwen.com/subject/ggdgkxtx.html