您的位置:首页 > 移动开发 > IOS开发

2分钟学会GCD

2014-05-26 22:55 519 查看
哈哈 骗你的了 怎么可能两分钟真正的学会GCD,但是我会用最简短的语言说明什么是GCD,不会耽误你太多时间。

先说说基本概念,再说说常用API

gcd是一个C语言的底层库代码,使用了高并发模型进行处理,而不是简单的锁和线程,使用GCD能优化你的程序性能,推迟大运算,调用多处理器,还能提供一些更完善的函数接口,例如单例。

GCD分两种形式的调用

同步调用:等待任务结束,线程阻塞dispatch_sync

异步调用:直接返回,线程不阻塞dispatch_async

GCD又分了三种队列

主队列:串行队列,在主线程执行,任务一个个挨着执行

4个不同优先级的全局调度队列:并行队列,同时执行任务的队列

自创队列:串行和并行自己选,这个好处是可控,可追溯

GCD的一些注意事项

很多时候是两个GCD嵌套使用的,比如说先处理数据再回调修改UI,或者先处理数据,再回调某些处理方法
可以使用dispatch_after来延迟执行方法,可以理解为延迟的dispatch_async
使用dispatch_once来处里某些线程安全的
dispatch_barrier可以用来作为读写锁,保证写入的时候没有任何读取操作

Dispatch
Group 会在整个组的任务都完成时通知你

说道 Group 这个倒是需要详细的说说,有时候使用它能帮助你解决很多不好处理的麻烦
他有两种实现方式,第一种是dispatch_group_wait,它会阻塞当前线程,类似一个线程池,进入一个计数+1,完成-1,也就是说只有在所有进入的任务全部完成,计数为0的时候才会结束此group,直接上代码

- (void)downloadPhotosWithCompletionBlock:(BatchPhotoDownloadingCompletionBlock)completionBlock
{
dispatch_async(dispatch_get_global_queue(DISPATCH_QUEUE_PRIORITY_HIGH, 0), ^{ // 1在一个异步队列中调用,不阻塞主线程

__block NSError *error;
dispatch_group_t downloadGroup = dispatch_group_create(); // 2创建组

for (NSInteger i = 0; i < 3; i++) {
NSURL *url;
switch (i) {
case 0:
url = [NSURL URLWithString:kOverlyAttachedGirlfriendURLString];
break;
case 1:
url = [NSURL URLWithString:kSuccessKidURLString];
break;
case 2:
url = [NSURL URLWithString:kLotsOfFacesURLString];
break;
default:

b10c
break;
}

dispatch_group_enter(downloadGroup); // 3进组组 +1
Photo *photo = [[Photo alloc] initwithURL:url
withCompletionBlock:^(UIImage *image, NSError *_error) {
if (_error) {
error = _error;
}
dispatch_group_leave(downloadGroup); // 4 退出组 -1
}];

[[PhotoManager sharedManager] addPhoto:photo];
}
dispatch_group_wait(downloadGroup, DISPATCH_TIME_FOREVER); // 5等待完成,设置超时
dispatch_async(dispatch_get_main_queue(), ^{ // 6 完成后回调
if (completionBlock) { // 7
completionBlock(error);
}
});
});
}

第二种dipath_group_notify其实和第一种一样,唯一的优点就是不需要先起一个异步队列了,它不会阻塞线程
直接上代码

- (void)downloadPhotosWithCompletionBlock:(BatchPhotoDownloadingCompletionBlock)completionBlock
{
// 1
__block NSError *error;
dispatch_group_t downloadGroup = dispatch_group_create();

for (NSInteger i = 0; i < 3; i++) {
NSURL *url;
switch (i) {
case 0:
url = [NSURL URLWithString:kOverlyAttachedGirlfriendURLString];
break;
case 1:
url = [NSURL URLWithString:kSuccessKidURLString];
break;
case 2:
url = [NSURL URLWithString:kLotsOfFacesURLString];
break;
default:
break;
}

dispatch_group_enter(downloadGroup); // 2
Photo *photo = [[Photo alloc] initwithURL:url
withCompletionBlock:^(UIImage *image, NSError *_error) {
if (_error) {
error = _error;
}
dispatch_group_leave(downloadGroup); // 3
}];

[[PhotoManager sharedManager] addPhoto:photo];
}

dispatch_group_notify(downloadGroup, dispatch_get_main_queue(), ^{ // 4
if (completionBlock) {
completionBlock(error);
}
});
}

最后再说点其他的,上面的for循环其实也可以用 dispath_apply 来代替的

我的两分钟教学就到此为止了,其实完全是照抄了大神的博客,然后就是缩缩缩,要想看大神

http://www.raywenderlich.com/63338/grand-central-dispatch-in-depth-part-1

http://www.raywenderlich.com/63338/grand-central-dispatch-in-depth-part-2
内容来自用户分享和网络整理,不保证内容的准确性,如有侵权内容,可联系管理员处理 点击这里给我发消息
标签:  gcd iOS