首先,我们来看下下面一个例子:

代码:(串行队列里同步线程嵌套)

    NSLog(@"haha");

    dispatch_queue_t queue = dispatch_queue_create("test", nil);

    dispatch_sync(queue, ^ {

        NSLog(@"xxoo0");

        dispatch_sync(queue, ^ {

            NSLog(@"xxoo1");

        });

        NSLog(@"xxoo2");

    });

运行结果:



2014-08-25 14:30:24.440 test[4424:60b] haha

2014-08-25 14:30:24.441 test[4424:60b] xxoo0



在test串行队列中,有两个同步线程嵌套导致第二个同步线程运行不了,产生了死锁。

原因是:在串行队列中,第二个同步线程要执行,必须等待第一个同步线程执行完成后才可进行,但是第一个同步线程要执行完又得等待第二个同步线程执行完,因为第二个同步线程嵌套在第一个同步线程里,这就造成了两个同步线程互相等待,即死锁。

特别强调:是在串行队列里!





    dispatch_queue_t queue = dispatch_queue_create("test", nil);

这行代码中,第二个参数为nil值,相当与值为DISPATCH_QUEUE_SERIAL,即为串行的。如果把值改成DISPATCH_QUEUE_CONCURRENT,即为并行的,就不会导致两个同步线程死锁。或者使用dispatch_get_global_queue(DISPATCH_QUEUE_PRIORITY_DEFAULT, 0)也行,因为dispatch_get_global_queue是并行队列。



ok,我们来看第二个例子:



代码:(主线程里的同步线程)



    NSLog(@"haha");

    dispatch_sync(dispatch_get_main_queue(), ^ {

        NSLog(@"xxoo");

    });

运行结果:



2014-08-25 15:01:58.922 test[4797:60b] haha



结果还是死锁,这个例子其实和第一个例子是类似的,主线程其实就是在一个串行队列里的,我们写的这个同步线程就相当与第一个例子的第二个嵌套的同步线程,因为这个同步线程是在主线程里写的,就相当于嵌套在主线程里的。



所以,对于

dispatch_sync(queue, ^{});

这行代码的意义可以概括为: 会阻塞当前线程等待串行queue中的所有任务执行完成后再向下执行。

关于dispatch_sync死锁问题的更多相关文章

  1. 【读书笔记】iOS-GCD-API

    一,Dispatch Queue dispatch_async(queue, ^{ /* *想执行的任务 */ }); 其中queue分为两种: 1,Serial Dispatch Queue 等待现 ...

  2. 第3月第19天 cxx_destruct dispatch_get_main_queue()死锁

    1. http://blog.jobbole.com/65028/ 2. - (void)viewDidLoad { [super viewDidLoad]; NSLog("); dispa ...

  3. GCD死锁 多线程

    NSLog("); dispatch_sync(dispatch_get_main_queue(), ^{ // sync同步 main串行 // 同步,异步--线程 同步-主线程 // m ...

  4. iOS gcd dispatch使用注意,dispatch_syn可能产生的死锁

      我们在使用dispatch_sync 时可能会出现死锁,看下面的例子: import UIKit class ViewController: UIViewController { var seri ...

  5. GCD中的dispatch_sync、dispatch_sync 分别与串行、并行队列组合执行小实验

    平常开发中会经常用gcd做一下多线程任务,但一直没有对同步.异步任务在串行.并行队列的执行情况做个全面的认识,今天写了个demo跑了下,还是有些新发现的. 代码如下: - (void)touchesB ...

  6. dispatch_sync may result in dead-lock

    以下代码会引起死锁 dispatch_block_t block = ^{ ; i < ; i++) { NSLog(@"dispatch_sync:%d", i); } } ...

  7. dispatch_async & dispatch_sync

    Clear that! dispatch_async 是将block发送到指定线程去执行,当前线程不会等待,会继续向下执行. dispatch_sync 也是将block发送到指定的线程去执行,但是当 ...

  8. iOS学习笔记-死锁deadlock理解

    1.首先看一下官方文档的解释,这个block的队列是同步执行的,不像异步,这个方法直到block执行完毕才会返回 2.主线程一旦开启,就要先把自己的代码执行完成之后,才去执行加入到主队列中的任务 De ...

  9. (iOS)关于GCD死锁的问题

    - (void)viewDidLoad { [super viewDidLoad]; dispatch_sync(dispatch_get_main_queue(), ^{NSLog("); ...

随机推荐

  1. GitHub 开启 Two-factor authentication,如何在命令行下更新和上传代码

    最近在使用GitHub管理代码,在git命令行管理代码时候遇到一些问题. 如果开起了二次验证(Two-factor authentication两个要素认证),命令行会一直提示输入用户名和密码.查找了 ...

  2. log4cpp安装使用

    1. 主页:http://log4cpp.sourceforge.net“Log4cpp is library of C++ classes for flexible logging to files ...

  3. 数据库之游标过程-- 基于MySQL

    实例如下: DROP PROCEDURE IF EXISTS pr_change_station_user_acct_his; -- 如果存在存储过程,即删除存储过程 create procedure ...

  4. jsp四大作用域之page

    <%@ page language="java" contentType="text/html; charset=utf-8" pageEncoding= ...

  5. 【UML】对象图Object diagram(转)

    http://blog.csdn.net/sds15732622190/article/details/48894751 前言 今天要说的是UML中的对象图.他与类图,合作图都有关系,是类图的实例化. ...

  6. UVA 11627 Slalom(二分)

    二分,判断的时候,一个点一个点的考虑肯定是不行啦,考虑的单位是一个区间, 每次左端点尽量向左边移动,右端点尽量向右,得到下次可以达到的范围,检查一下和下一个区间有没有交集. #include<b ...

  7. JS中的作用域和作用域链

    本文原链接:https://cloud.tencent.com/developer/article/1403589 前言 作用域(Scope) 1. 什么是作用域 2. 全局作用域和函数作用域 3. ...

  8. DROP OPERATOR CLASS - 删除一个操作符类

    SYNOPSIS DROP OPERATOR CLASS name USING index_method [ CASCADE | RESTRICT ] DESCRIPTION 描述 DROP OPER ...

  9. 实验十二 团队作业8:软件测试与Alpha冲刺

    实验十二 团队作业8:软件测试与Alpha冲刺 实验时间 2018-6-13 Deadline: [6.13-6.19]之间任选连续5天的23:00,以团队随笔博文提交时间为准. 评分标准: 按时交 ...

  10. 伪基站SSRP

    伪基站的基本构成包括一台发射主机.一台笔记本电脑.一根天线.一部手机和电源.其中,手机用来测得频点,即某个区域运营商正规基站的频点,然后再把频点和短信内容输入到电脑安装好的程序,通过发射主机和天线进行 ...