IOS开发多线程GCD的学习(二)

本文深入探讨了Grand Central Dispatch (GCD) 的多种高级用法,包括确保代码仅执行一次的dispatch_once、任务组dispatch_group_t的应用、实现延迟执行的dispatch_after、循环任务调度dispatch_apply、并行队列下保证单线程执行的dispatch_barrier_async,以及队列的暂停与恢复等。通过实例展示了如何在iOS开发中高效地使用这些特性。

1、dispatch_once的使用

     (1)dispatch_once 多用来确保某段代码只执行一次,多用来进行单例的创建  

+ (id)shareInstance

{

    static dispatch_once_t onceToken;

    dispatch_once(&onceToken,^{

         _shareInstance = [[self alloc] init];

    });

    return _shareInstance;

}

2、任务组dispatch_group_t

   (1)使用场景:有时我们需要多个任务同时(在多个线程里)执行,在他们完成后再去执行其他的任务

   (2)使用例子:thread1、thread2、thread3的执行顺序不确定,执行完1、2、3后方可执行done;    

dispatch_queue_t queue = dispatch_get_global_queue(DISPATCH_QUEUE_PRIORITY_DEFAULT, 0);

    dispatch_group_t group = dispatch_group_create();

    dispatch_group_async(group, queue, ^{

        NSLog(@"thread1");

    });

    dispatch_group_async(group, queue, ^{

        NSLog(@"thread2");

    });

    dispatch_group_async(group, queue, ^{

        NSLog(@"thread3");

    });

    dispatch_group_notify(group, dispatch_get_main_queue()  , ^{

        NSLog(@"done");

    });

3、dispatch_after
    (1)功能:延迟一段时间把任务提交到队列中执行,返回之后就不能取消,通常用来执行在主队列上延迟执行一项任务
      (2) 函数原型:
            func dispatch_after(_when:dispatch_time_t,//时间间隔
                                         _queue:dispatch_queue_t!,//提交到的队列
                                         _block:dispatch_block_t!//执行的任务
)
    (3)使用的例子,利用dispatch_after写一个自己用的delay函数,在view载入完成后,延迟给用户一个提示,也可以给这个提示添加一些动画,                  要比view在载入完成直接显示提示要有好的多。
           

      typedef void (^complete)(void);

      //自定义方法

      - (void)delay:(double)delayTime toDo:(complete)complete

     {

          dispatch_after(dispatch_time(DISPATCH_TIME_NOW, (delayTime*NSEC_PER_SEC)),         dispatch_get_main_queue(), complete);

     }

        

    //方法调用

    [self delay:3 toDo:^{

        UIAlertView *alert = [[UIAlertView alloc]initWithTitle:@"alert" message:@"delay alert" delegate:self         cancelButtonTitle:@"ok" otherButtonTitles: nil];

        [alert show];

    }];

4、dispatch_apply
     (1)功能:把一项任务提交到队列中多次执行,具体是并行执行还是串行执行由队列本身决定,dispatch_apply不会立刻返回,在执行完毕后才                      会返回,是同步的调用
       (2) 函数原型:

       void dispatch_apply(size_t iterations, //执行的次数

                           dispatch_queue_t queue,//提交的队列

                           void (^block)(size_t));//执行的任务

   (3)使用场景:把不相关的循环提交到后台线程并行执行,并且循环任务调度到后台执行的效率提高,能抵消掉队列调度本身的开销,那么效率                                会显著提高

dispatch_queue_t queue = dispatch_get_global_queue(DISPATCH_QUEUE_PRIORITY_DEFAULT, 0);

    dispatch_apply(20, queue, ^(size_t i) {

        NSLog(@"%lu", i);

    });

       注意:这段代码让i并行循环了20次,如果内部处理的是一个数组,就可以实现对数组的并行循环了,它的内部是dispatch_sync的同          步操作,所以在执行这个循环的过程当中,当前线程会被阻塞。

 5、dispatch_barrier_async
     (1)功能:并行队列下,保证在某个时间段内,只执行一个线程  
     (2)函数原型: 

    void dispatch_barrier_async(dispatch_queue_t queue, dispatch_block_t block);

   (3)使用场景:对于没有数据竞争的并行操作,则可以使用并行队列(CONCURRENT)来实现,例子:  

    dispatch_queue_t queue1 = dispatch_get_global_queue(DISPATCH_QUEUE_PRIORITY_DEFAULT, 0);

    dispatch_async(queue1, ^{

        NSLog(@"1");

    });

    dispatch_async(queue1, ^{

        NSLog(@"2");

    });

    dispatch_barrier_async(queue1, ^{

        NSLog(@"3");

    });

    dispatch_async(queue1, ^{

        NSLog(@"4");

    });

    dispatch_async(queue1, ^{

        NSLog(@"5");

    });

      注意:这样1、2、3、4、5的执行顺序仍然不能确定,但是可以保证在执行3的时候无其他线程操作,直至3执行完毕
6、线程的暂停和恢复
    (1) 使用dispatch_suspend(queue)可以暂停队列中任务的执行,
    (2) 使用dispatch_result(queue)可以继续执行被暂停的队列

评论
成就一亿技术人!
拼手气红包6.0元
还能输入1000个字符
 
红包 添加红包
表情包 插入表情
 条评论被折叠 查看
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值