iOS深入理解GCD 第三篇(dispatch_group_enter和dispatch_group_leave)

一直对dispatch_group_enter(group)、dispatch_group_leave(group)很陌生,最近看了几篇博客,整理一下权当理解记忆
Calling this function indicates another block has joined the group through
  a means other than dispatch_group_async(). Calls to this function must be
 * balanced with dispatch_group_leave().
调用这个方法标志着一个代码块被加入了group,和dispatch_group_async功能类似;
需要和dispatch_group_enter()、dispatch_group_leave()成对出现;
void
dispatch_group_enter(dispatch_group_t group);

个人理解:和内存管理的引用计数类似,我们可以认为group也持有一个整形变量(只是假设),当调用enter时计数加1,调用leave时计数减1,当计数为0时会调用dispatch_group_notify并且dispatch_group_wait会停止等待;

以上内容摘自 http://www.jianshu.com/p/228403206664 作者:liang1991

代码示例:(取自)http://www.jianshu.com/p/471469ad9af1 作者:老马的春天

- (void)test {
    NSURL *url = [NSURL URLWithString:@"http://upload-images.jianshu.io/upload_images/1432482-dcc38746f56a89ab.png?imageMogr2/auto-orient/strip%7CimageView2/2/w/1240"];

    SDWebImageManager *manager = [SDWebImageManager sharedManager];

    dispatch_group_t group = dispatch_group_create();

    dispatch_group_enter(group);
    [manager loadImageWithURL:url options:SDWebImageRefreshCached progress:nil completed:^(UIImage * _Nullable image, NSData * _Nullable data, NSError * _Nullable error, SDImageCacheType cacheType, BOOL finished, NSURL * _Nullable imageURL) {
        dispatch_group_leave(group);
    }];

    dispatch_group_notify(group, dispatch_get_main_queue(), ^{
        NSLog(@"下载完成了");
    });
}

enter和leave方法必须成对出现,如果调用leave的次数多于enter就会崩溃,当我们使用SD时,如果Options设置为SDWebImageRefreshCached,那么这个completionBlock至少会调用两次,首先返回缓存中的图片。其次在下载完成后再次调用Block,这也就是崩溃的原因。

要想重现上边方法的崩溃,等图片下载完之后,再从新调用该方法就行。

你可能感兴趣的:(iOS深入理解GCD 第三篇(dispatch_group_enter和dispatch_group_leave))