ios-关于GCD的进阶使用

/**

 dispatch_after

 该函数用于任务延时执行,其中参数dispatch_time_t代表延时时长,dispatch_queue_t代表使用哪个队列。如果队列未主队列,那么任务在主线程执行,如果队列为全局队列或者自己创建的队列,那么任务在子线程执行(适用于做倒计时)

 */

-(void)GCDDelay{

    //主队列延时

    dispatch_time_t when_main = dispatch_time(DISPATCH_TIME_NOW, (int64_t)(3.0 * NSEC_PER_SEC));

    dispatch_after(when_main, dispatch_get_main_queue(), ^{

        NSLog(@"main_%@",[NSThread currentThread]);

    });

    //全局队列延时

    dispatch_time_t when_global = dispatch_time(DISPATCH_TIME_NOW, (int64_t)(4.0 * NSEC_PER_SEC));

    dispatch_after(when_global, dispatch_get_global_queue(DISPATCH_QUEUE_PRIORITY_DEFAULT, 0), ^{

        NSLog(@"global_%@",[NSThread currentThread]);

    });

    //自定义队列延时

    dispatch_time_t when_custom = dispatch_time(DISPATCH_TIME_NOW, (int64_t)(5.0 * NSEC_PER_SEC));

    dispatch_after(when_custom, self.serialQueue, ^{

        NSLog(@"custom_%@",[NSThread currentThread]);

    });

}

执行结果如下:

2017-09-14 14:54:38.034 GCDTest[37203:63373201] main_<NSThread: 0x608000261600>{number = 1, name = main}

2017-09-14 14:54:39.404 GCDTest[37203:63373265] global_<NSThread: 0x6080002762c0>{number = 3, name = (null)}

2017-09-14 14:54:40.034 GCDTest[37203:63373265] custom_<NSThread: 0x6080002762c0>{number = 3, name = (null)}


/**

 dispatch_once

 保证函数在整个生命周期内只会执行一次,保证button只能点击一次有效

 */

- (IBAction)touchesButton:(id)sender {

    static dispatch_once_t onceToken;

    dispatch_once(&onceToken, ^{

        NSLog(@"%@",[NSThread currentThread]);

    });

}


/**

 dispatch_group_async & dispatch_group_notify

 队列组:当加入到队列组中的所有任务执行完成之后,会调用dispatch_group_notify函数通知任务全部完成

 */

-(void)GCDGroup{

    //

    [self jointImageView];

    //

    dispatch_group_t group = dispatch_group_create();

    __block UIImage *image_1 = nil;

    __block UIImage *image_2 = nil;

    //group中添加一个任务

    dispatch_group_async(group, dispatch_get_global_queue(DISPATCH_QUEUE_PRIORITY_DEFAULT, 0), ^{

        image_1 = [UIImage imageWithData:[NSData dataWithContentsOfURL:[NSURL URLWithString:@"https://timgsa.baidu.com/timg?image&quality=80&size=b9999_10000&sec=1502706256731&di=371f5fd17184944d7e2b594142cd7061&imgtype=0&src=http%3A%2F%2Fimg4.duitang.com%2Fuploads%2Fitem%2F201605%2F14%2F20160514165210_LRCji.jpeg"]]];

        

    });

    dispatch_group_async(group, dispatch_get_global_queue(DISPATCH_QUEUE_PRIORITY_DEFAULT, 0), ^{

        image_2 = [UIImage imageWithData:[NSData dataWithContentsOfURL:[NSURL URLWithString:@"https://ss3.bdstatic.com/70cFv8Sh_Q1YnxGkpoWK1HF6hhy/it/u=776127947,2002573948&fm=26&gp=0.jpg"]]];

    });

    //group中所有任务执行完毕,通知该方法执行

    dispatch_group_notify(group, dispatch_get_main_queue(), ^{

        self.imageView_1.image = image_1;

        self.imageView_2.image = image_2;

        //

        UIGraphicsBeginImageContextWithOptions(CGSizeMake(200, 100), NO, 0.0f);

        [image_2 drawInRect:CGRectMake(0, 0, 100, 100)];

        [image_1 drawInRect:CGRectMake(100, 0, 100, 100)];

        UIImage *image_3 = UIGraphicsGetImageFromCurrentImageContext();

        self.imageView_3.image = image_3;

        UIGraphicsEndImageContext();

    });

}

-(void)jointImageView{

    self.imageView_1 = [[UIImageView alloc] initWithFrame:CGRectMake(20, 50, 100, 100)];

    [self.view addSubview:_imageView_1];

    

    self.imageView_2 = [[UIImageView alloc] initWithFrame:CGRectMake(140, 50, 100, 100)];

    [self.view addSubview:_imageView_2];

    

    self.imageView_3 = [[UIImageView alloc] initWithFrame:CGRectMake(20, 200, 200, 100)];

    [self.view addSubview:_imageView_3];

    

    self.imageView_1.layer.borderColor = self.imageView_2.layer.borderColor = self.imageView_3.layer.borderColor = [UIColor grayColor].CGColor;

    self.imageView_1.layer.borderWidth = self.imageView_2.layer.borderWidth = self.imageView_3.layer.borderWidth = 1;

}

执行结果如下:

/**

 dispatch_barrier_async

 使用此方法创建的任务,会查找当前队列中有没有其他任务要执行,如果有,则等待已有任务执行完毕后再执行,同时,在此任务之后进入队列的任务,需要等待此任务执行完成后,才能执行

 */

-(void)GCDbarrier{

    dispatch_async(self.concurrentQueue, ^{

        NSLog(@"dispatch-1");

    });

    NSLog(@"iphone8X");

    dispatch_async(self.concurrentQueue, ^{

        NSLog(@"dispatch-2");

    });

    dispatch_barrier_sync(self.concurrentQueue, ^{

        NSLog(@"任务barrier");

    });

    NSLog(@"iphoneX");

    dispatch_async(self.concurrentQueue, ^{

        NSLog(@"dispatch-3");

    });

    NSLog(@"iphone8");

    dispatch_async(self.concurrentQueue, ^{

        NSLog(@"dispatch-4");

    });

}

执行结果如下:

2017-09-14 15:03:51.339 GCDTest[37376:63399267] iphone8X

2017-09-14 15:03:51.339 GCDTest[37376:63399328] dispatch-1

2017-09-14 15:03:51.339 GCDTest[37376:63399328] dispatch-2

2017-09-14 15:03:51.339 GCDTest[37376:63399267] 任务barrier

2017-09-14 15:03:51.340 GCDTest[37376:63399267] iphoneX

2017-09-14 15:03:51.340 GCDTest[37376:63399267] iphone8

2017-09-14 15:03:51.340 GCDTest[37376:63399328] dispatch-3

2017-09-14 15:03:51.340 GCDTest[37376:63399328] dispatch-4


/**

 dispatch_apply

 该函数用于重复执行某个任务,如果任务队列是并行队列,重复执行的任务会并发执行,如果任务队列为串行队列,则任务会顺序执行,该函数为同步函数,要防止线程阻塞和死锁

 */

-(void)GCDApply{

    //重复执行 串行

    dispatch_apply(5, self.serialQueue, ^(size_t i) {

        NSLog(@"%@_%@",@(i),[NSThread currentThread]);

    });

    NSLog(@"----------------------");

    //重复执行 并行  执行顺序随机  有时跟输出结果会不一致

    dispatch_apply(5, self.concurrentQueue, ^(size_t i) {

        NSLog(@"%@_%@",@(i),[NSThread currentThread]);

    });

    

    //主线程执行同步报异常

//    dispatch_apply(5, dispatch_get_main_queue(), ^(size_t i) {

//        NSLog(@"%@_%@",@(i),[NSThread currentThread]);

//    });

}

执行结果如下:

2017-09-14 15:07:54.568 GCDTest[37523:63411305] 0_<NSThread: 0x60000007a8c0>{number = 1, name = main}

2017-09-14 15:07:54.569 GCDTest[37523:63411305] 1_<NSThread: 0x60000007a8c0>{number = 1, name = main}

2017-09-14 15:07:54.569 GCDTest[37523:63411305] 2_<NSThread: 0x60000007a8c0>{number = 1, name = main}

2017-09-14 15:07:54.570 GCDTest[37523:63411305] 3_<NSThread: 0x60000007a8c0>{number = 1, name = main}

2017-09-14 15:07:54.570 GCDTest[37523:63411305] 4_<NSThread: 0x60000007a8c0>{number = 1, name = main}

2017-09-14 15:07:54.570 GCDTest[37523:63411305] ----------------------

2017-09-14 15:07:54.570 GCDTest[37523:63411305] 0_<NSThread: 0x60000007a8c0>{number = 1, name = main}

2017-09-14 15:07:54.571 GCDTest[37523:63411374] 1_<NSThread: 0x608000261700>{number = 3, name = (null)}

2017-09-14 15:07:54.571 GCDTest[37523:63411371] 2_<NSThread: 0x608000261740>{number = 4, name = (null)}

2017-09-14 15:07:54.571 GCDTest[37523:63411389] 3_<NSThread: 0x60000026a040>{number = 5, name = (null)}

2017-09-14 15:07:54.571 GCDTest[37523:63411305] 4_<NSThread: 0x60000007a8c0>{number = 1, name = main}






  • 0
    点赞
  • 0
    收藏
    觉得还不错? 一键收藏
  • 0
    评论

“相关推荐”对你有帮助么?

  • 非常没帮助
  • 没帮助
  • 一般
  • 有帮助
  • 非常有帮助
提交
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

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

抵扣说明:

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

余额充值