为什么异步阻止执行阻塞主线程?

时间:2016-04-20 10:16:41

标签: ios objective-c afnetworking grand-central-dispatch

我有一个使用AFNetworking发送请求的应用程序,在完成下载后,它会调用阻止我从JSON创建数据模型的地方。在模型初始化期间,使用以下代码加载异步图像

dispatch_async(dispatch_get_global_queue(DISPATCH_QUEUE_PRIORITY_DEFAULT, 0), ^{
   NSData *urlData = [NSData dataWithContentsOfURL:downloadURL];
}

我知道dataWithContentsOfURL:是同步的,并且符合https://developer.apple.com/library/mac/documentation/Cocoa/Reference/Foundation/Classes/NSData_Class/#//apple_ref/occ/clm/NSData/dataWithContentsOfURL

  

...这个方法可以在缓慢的情况下阻止当前线程持续数十秒   网络...

但是由于它在其他线程中异步执行,它不应该阻止主线程。经过一些调查,我发现从URLSession:task:didCompleteWithError:内部的AFURLSessionManager.m方法开始,具有以下块层次结构

URLSession:task:didCompleteWithError: //1
    |
   dispatch_async(url_session_manager_processing_queue(), ^{  //2
   //url_session_manager_processing_queue() - this is the default queue
       |
      dispatch_group_async(url_session_manager_completion_group(), dispatch_get_main_queue(), ^{ //3
          |
         //Inside of my callback
         dispatch_async(dispatch_get_global_queue(DISPATCH_QUEUE_PRIORITY_DEFAULT, 0), ^{ //4
            |
           NSData *urlData = [NSData dataWithContentsOfURL:downloadURL];

如果我设置AFHTTPSessionManager' s completionQueue属性:

_sharedClient.completionQueue = dispatch_get_global_queue(DISPATCH_QUEUE_PRIORITY_DEFAULT, 0);

然后dispatch_group_sync ... //3使用默认队列,而不是主线程和主线程未被阻止。有人可以解释为什么不设置completionQueue属性我的主线程被阻止了吗? (在主线程中显示semaphore_wait_trap的堆栈跟踪)

0 个答案:

没有答案