GCD的group方法只有async(異步方法)即
void dispatch_group_async(dispatch_group_t group,
dispatch_queue_t queue,
dispatch_block_t block);
使用group要傳2個(gè)參數(shù) group、queue财著,其中g(shù)roup使用
//創(chuàng)建group
dispatch_group_t group = dispatch_group_create();
queue我們可以使用以下幾種方式
dispatch_queue_t queue = dispatch_get_main_queue()
//或者
queue = dispatch_get_global_queue(0, 0);
//或者 并行隊(duì)列
queue = dispatch_queue_create("com.sccc", DISPATCH_QUEUE_CONCURRENT);
//或者串行隊(duì)列
queue = dispatch_queue_create("com.sccc", DISPATCH_QUEUE_SERIAL);
這里主要區(qū)分串行和并行的方式
- (void)doSomething:(void (^)())handler {
if (handler) {
sleep(2);
handler();
}
}
//異步串行g(shù)roup
- (void)groupAsyncSerialTest {
//創(chuàng)建串行隊(duì)列
dispatch_queue_t queue = dispatch_queue_create("com.sccc", DISPATCH_QUEUE_SERIAL);
dispatch_group_t group = dispatch_group_create();
dispatch_group_async(group, queue, ^{
[self doSomething:^() {
NSLog(@"任務(wù)一");
}];
});
dispatch_group_async(group, queue, ^{
[self doSomething:^() {
NSLog(@"任務(wù)二");
}];
});
dispatch_group_async(group, queue, ^{
[self doSomething:^() {
NSLog(@"任務(wù)三");
}];
});
dispatch_group_notify(group, queue, ^{
NSLog(@"前面的任務(wù)已完成");
});
}
結(jié)果
值得注意的是按照順序每2s打印一次
串行隊(duì)列的情況如下:
//異步并行
- (void)groupAsyncConcurrentTest {
//創(chuàng)建并行隊(duì)列
dispatch_queue_t queue = dispatch_queue_create("com.sccc", DISPATCH_QUEUE_CONCURRENT);
queue = dispatch_get_global_queue(0, 0);
dispatch_group_t group = dispatch_group_create();
dispatch_group_async(group, queue, ^{
[self doSomething:^() {
NSLog(@"任務(wù)一");
}];
});
dispatch_group_async(group, queue, ^{
[self doSomething:^() {
NSLog(@"任務(wù)二");
}];
});
dispatch_group_async(group, queue, ^{
[self doSomething:^() {
NSLog(@"任務(wù)三");
}];
});
dispatch_group_notify(group, queue, ^{
NSLog(@"前面的任務(wù)已完成");
});
}
結(jié)果如下
多次試驗(yàn)總結(jié)的結(jié)果是任務(wù)完成先后順序不定,前面的任務(wù)都完成后才會(huì)執(zhí)行notify中的任務(wù)
當(dāng)然以上的情況不適用于網(wǎng)絡(luò)請(qǐng)求
網(wǎng)絡(luò)請(qǐng)求使用group時(shí)需要注意
dispatch_group_enter(group);
dispatch_group_leave(group);
搭配使用
下面是沒(méi)有搭配使用的情況
//異步并行
- (void)groupAsyncConcurrentTest {
//創(chuàng)建并行隊(duì)列
dispatch_queue_t queue = dispatch_queue_create("com.sccc", DISPATCH_QUEUE_CONCURRENT);
queue = dispatch_get_global_queue(0, 0);
dispatch_group_t group = dispatch_group_create();
dispatch_group_async(group, queue, ^{
[[CMAppRequest sharedInstance] guideMessage:^() {
NSLog(@"任務(wù)一");
}];
});
dispatch_group_async(group, queue, ^{
[[CMAppRequest sharedInstance] guideMessage:^() {
NSLog(@"任務(wù)二");
}];
});
dispatch_group_async(group, queue, ^{
[[CMAppRequest sharedInstance] guideMessage:^() {
NSLog(@"任務(wù)三");
}];
});
dispatch_group_notify(group, queue, ^{
NSLog(@"前面的任務(wù)已完成");
});
}
結(jié)果如下
你會(huì)發(fā)現(xiàn)notify不起作用了许起,這時(shí)候就要用到enter、leave了
修改代碼如下:
//異步并行
- (void)groupAsyncConcurrentTest {
//創(chuàng)建并行隊(duì)列
dispatch_queue_t queue = dispatch_queue_create("com.sccc", DISPATCH_QUEUE_CONCURRENT);
queue = dispatch_get_global_queue(0, 0);
dispatch_group_t group = dispatch_group_create();
dispatch_group_enter(group);
[[CMAppRequest sharedInstance] guideMessage:^() {
dispatch_group_leave(group);
NSLog(@"任務(wù)一");
}];
dispatch_group_enter(group);
[[CMAppRequest sharedInstance] guideMessage:^() {
dispatch_group_leave(group);
NSLog(@"任務(wù)二");
}];
dispatch_group_enter(group);
[[CMAppRequest sharedInstance] guideMessage:^() {
dispatch_group_leave(group);
NSLog(@"任務(wù)三");
}];
dispatch_group_notify(group, queue, ^{
NSLog(@"前面的任務(wù)已完成");
});
}
//考慮到請(qǐng)求是異步隊(duì)列窜锯,不在需要使用dispatch_group_async
結(jié)果如下:
這就正常了,網(wǎng)絡(luò)請(qǐng)求的就不在做串行和并行的測(cè)試了,以上網(wǎng)絡(luò)請(qǐng)求部分使用的是串行隊(duì)列敦间,串行的打印結(jié)果只和網(wǎng)絡(luò)請(qǐng)求的返回順序有關(guān)。
- 最后特別需要注意束铭,enter和leave一定要成對(duì)出現(xiàn)廓块;否則如實(shí)enter多了,notify里的任務(wù)就會(huì)永遠(yuǎn)執(zhí)行不了纯露,若是levae多了則會(huì)照成crash
當(dāng)然這只是group的一部分還有dispatch_group_wait等功能沒(méi)有一一實(shí)現(xiàn)剿骨,以上內(nèi)容只代表個(gè)人觀點(diǎn)代芜,如有問(wèn)題歡迎指正埠褪,謝謝~~