iOS进阶_GCD(三.延时执行&一次执行&调度组&主队列)

延迟执行

- (void)touchesBegan:(NSSet<UITouch *> *)touches withEvent:(UIEvent *)event {
    [self delay];
}
-(void)delay{
    NSLog(@"come here");
    /**
     参数:
      1.when 时间 从现在开始,经过多少纳秒之后,让queue队列调度block任务,异步执行
      2.queue 队列
      3.block 代码块
     */
    dispatch_time_t when = dispatch_time(DISPATCH_TIME_NOW, (int64_t)(1.0 * NSEC_PER_SEC));
    dispatch_queue_t q = dispatch_queue_create("WT_queue", NULL);
    dispatch_after(when, q, ^{
        NSLog(@"%@",[NSThread currentThread]);
    });
}

一次执行

在单例设计模式中非常普遍,苹果提供了 一次执行机制,不仅能够保证一次执行而且是线程安全的
苹果推荐使用gcd 一次执行,效率高
不要使用互斥锁,效率低

- (void)touchesBegan:(NSSet<UITouch *> *)touches withEvent:(UIEvent *)event {
    [self testOnce];
}
-(void)once{
    NSLog(@"来了!!");
    static dispatch_once_t onceToken;
    NSLog(@"%ld",onceToken);
    dispatch_once(&onceToken, ^{
        //只会执行一次
        NSLog(@"执行了%@",[NSThread currentThread]);
    });
}

-(void)testOnce{
    for (int i=0;i<10; i++) {
        dispatch_async(dispatch_get_global_queue(0, 0), ^{
            [self once];
        });
    }
}

调度组

- (void)touchesBegan:(NSSet<UITouch *> *)touches withEvent:(UIEvent *)event {
    [self group1];
}

-(void)group1{
    //1.队列
    dispatch_queue_t q = dispatch_get_global_queue(0, 0);

    //2.调度组
    dispatch_group_t g = dispatch_group_create();

    //3.添加任务,让队列调度,任务执行情况,最后通知群组
    dispatch_group_async(g, q, ^{
        NSLog(@"download A%@",[NSThread currentThread]);
    });

    dispatch_group_async(g, q, ^{
        [NSThread sleepForTimeInterval:1.0];
        NSLog(@"download B%@",[NSThread currentThread]);
    });

    dispatch_group_async(g, q, ^{
        [NSThread sleepForTimeInterval:1.0];
        NSLog(@"download C%@",[NSThread currentThread]);
    });

    //4.所有任务执行完毕后,通知
    //用一个调度组,可以监听全局队列的任务,主队列去执行最后的任务
    //dispatch_group_notify 本身也是异步的
    dispatch_group_notify(g, dispatch_get_main_queue(), ^{
        //更新UI,通知用户
        NSLog(@"OK %@",[NSThread currentThread]);
    });

    NSLog(@"come here");
}

主队列

- (void)touchesBegan:(NSSet<UITouch *> *)touches withEvent:(UIEvent *)event {
    //[self gcdDemo1];//主队列异步任务
    //[self gcdDemo2];//线程死锁
    [self gcdDemo3];//主队列同步任务,放在子线程,不死锁
}
//同步任务死锁:当前是在主线程,让主队列执行同步任务!
//MARK:主队列同步任务(不死锁的)
-(void)gcdDemo3{
    void (^task)(void)=^{
        NSLog(@"这里!!%@",[NSThread currentThread]);
        //1.队列 --一启动主线程,就可以获取主队列
        dispatch_queue_t q = dispatch_get_main_queue();

        //2.同步任务
        dispatch_sync(q, ^{
            NSLog(@"能来吗?%@",[NSThread currentThread]);
        });
        NSLog(@"睡一会");
        [NSThread sleepForTimeInterval:1.0];
        NSLog(@"come here");
    };
    dispatch_async(dispatch_get_global_queue(0, 0), task);
}


/**
 主队列 & 串行队列的区别
 都是 一个一个安排任务
 队列特点:FIFO

 -并发队列:可以调度很多任务
 -串行队列:必须等待一个任务执行完成,再调度另外一个
   - 最多只能开启一条线程
 -主队列,以FIFO调度任务,如果主线程上面有任务在执行,主队列就不会调度任务
   - 主要是负责在主线程上执行任务
 */

-(void)gcdDemo2{

    //主队列是专门负责在主线程上调度任务的队列 --》不会开现场

    //1.队列 --一启动主线程,就可以获取主队列
    dispatch_queue_t q = dispatch_get_main_queue();

    //2.同步任务:同步执行的任务特点:这句话不执行完毕,就不能执行下一句,阻塞式
    dispatch_sync(q, ^{
        NSLog(@"%@",[NSThread currentThread]);
    });//互相锁死

    NSLog(@"come here");
}

-(void)gcdDemo1{
    //主队列是专门负责在主线程上调度任务的队列 --》不会开线程

    //1.队列 --一启动主线程,就可以获取主队列
    dispatch_queue_t q = dispatch_get_main_queue();

    //2.异步任务
    dispatch_async(q, ^{
        NSLog(@"%@",[NSThread currentThread]);
    });
    for (int i=0; i<10; i++) {
        NSLog(@"come here");
    }
}

这里写图片描述

  • 1
    点赞
  • 0
    收藏
    觉得还不错? 一键收藏
  • 0
    评论
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

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

抵扣说明:

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

余额充值