美文网首页
iOS开发之——GCD基础用法

iOS开发之——GCD基础用法

作者: 天空像天空一样蓝 | 来源:发表于2018-06-01 13:47 被阅读0次

没有怎么整理看起来有点乱,本文只是介绍GCD的基础用法

  • 任务队列

队列的创建方法/获取方法

//创建串行对列 SERIAL
    dispatch_queue_t serialQueue = dispatch_queue_create("serialQueue", DISPATCH_QUEUE_SERIAL);
    // 创建并发队列 CONCURRENT
    dispatch_queue_t concurrentQueue = dispatch_queue_create("concurrentQueue", DISPATCH_QUEUE_CONCURRENT);
    
    //串行队列 获取主队列的方法
    dispatch_queue_t mainQueue = dispatch_get_main_queue();
    //并发队列,获取全局并发队列
    dispatch_queue_t globalQueue = dispatch_get_global_queue(DISPATCH_QUEUE_PRIORITY_DEFAULT, 0);

创建任务

dispatch_queue_t queue = dispatch_queue_create("concurrentQueue", DISPATCH_QUEUE_CONCURRENT);
    // 同步执行任务创建方法
    dispatch_sync(queue, ^{
        // 同步执行任务代码
    });
    // 异步执行任务创建方法
    dispatch_async(queue, ^{
        // 异步执行任务代码
    });

同步+并发 在当前线程中执行任务,不会开启新的线程,执行完一个任务,在执行下一个任务

NSLog(@"currentThread---%@", [NSThread currentThread]);
    NSLog(@"syncConcurrent--begin");
    
    dispatch_queue_t queue = dispatch_queue_create("syncConcurrent", DISPATCH_QUEUE_CONCURRENT);
    
    dispatch_sync(queue, ^{
        // 追加任务1
        for (int i = 0; i < 2; i++) {
            [NSThread sleepForTimeInterval:2]; // 模拟耗时操作
            NSLog(@"1----%@", [NSThread currentThread]); // 打印当前线程
        }
    });
    
    dispatch_sync(queue, ^{
        // 追加任务2
        for (int i = 0; i < 2; i++) {
            [NSThread sleepForTimeInterval:2]; // 模拟耗时操作
            NSLog(@"2----%@", [NSThread currentThread]); // 打印当前线程
        }
    });
    
    dispatch_sync(queue, ^{
        // 追加任务3
        for (int i = 0; i < 2; i++) {
            [NSThread sleepForTimeInterval:2]; // 模拟耗时操作
            NSLog(@"3----%@", [NSThread currentThread]); // 打印当前线程
        }
    });
    
    NSLog(@"syncConcurrent--end");

异步+并发 可以开发多个线程,任务交替(同时)执行

NSLog(@"currentThread---%@", [NSThread currentThread]);
    NSLog(@"asyncConcurrent--begin");
    
    dispatch_queue_t queue = dispatch_queue_create("asyncConcurrent", DISPATCH_QUEUE_CONCURRENT);
    
    dispatch_async(queue, ^{
        // 追加任务1
        for (int i = 0; i < 2; i++) {
            [NSThread sleepForTimeInterval:2]; // 模拟耗时操作
            NSLog(@"1----%@", [NSThread currentThread]); // 打印当前线程
        }
    });
    
    dispatch_async(queue, ^{
        // 追加任务2
        for (int i = 0; i < 2; i++) {
            [NSThread sleepForTimeInterval:2]; // 模拟耗时操作
            NSLog(@"2----%@", [NSThread currentThread]); // 打印当前线程
        }
    });
    
    dispatch_async(queue, ^{
        // 追加任务3
        for (int i = 0; i < 2; i++) {
            [NSThread sleepForTimeInterval:2]; // 模拟耗时操作
            NSLog(@"3----%@", [NSThread currentThread]); // 打印当前线程
        }
    });
    
    NSLog(@"asyncConcurrent--end");

同步+串行 不会开启新线程,在当前线程执行任务,任务是串行的,执行完一个任务,在执行下一个任务

NSLog(@"currentThread---%@", [NSThread currentThread]);
    NSLog(@"syncSerial--begin");
    
    dispatch_queue_t queue = dispatch_queue_create("syncSerial", DISPATCH_QUEUE_SERIAL);
    
    dispatch_sync(queue, ^{
        // 追加任务1
        for (int i = 0; i < 2; i++) {
            [NSThread sleepForTimeInterval:2]; // 模拟耗时操作
            NSLog(@"1----%@", [NSThread currentThread]); // 打印当前线程
        }
    });
    
    dispatch_sync(queue, ^{
        // 追加任务2
        for (int i = 0; i < 2; i++) {
            [NSThread sleepForTimeInterval:2]; // 模拟耗时操作
            NSLog(@"2----%@", [NSThread currentThread]); // 打印当前线程
        }
    });
    
    dispatch_sync(queue, ^{
        // 追加任务3
        for (int i = 0; i < 2; i++) {
            [NSThread sleepForTimeInterval:2]; // 模拟耗时操作
            NSLog(@"3----%@", [NSThread currentThread]); // 打印当前线程
        }
    });
    
    NSLog(@"syncSerial--end");

异步+串行队列 会开启新的线程,但是因为任务是串行的,执行完一个任务后,在执行下一个任务

NSLog(@"currentThread---%@", [NSThread currentThread]);
    NSLog(@"asyncSerial--begin");
    
    dispatch_queue_t queue = dispatch_queue_create("asyncSerial", DISPATCH_QUEUE_SERIAL);
    
    dispatch_async(queue, ^{
        // 追加任务1
        for (int i = 0; i < 2; i++) {
            [NSThread sleepForTimeInterval:2]; // 模拟耗时操作
            NSLog(@"1----%@", [NSThread currentThread]); // 打印当前线程
        }
    });
    
    dispatch_async(queue, ^{
        // 追加任务2
        for (int i = 0; i < 2; i++) {
            [NSThread sleepForTimeInterval:2]; // 模拟耗时操作
            NSLog(@"2----%@", [NSThread currentThread]); // 打印当前线程
        }
    });
    
    dispatch_async(queue, ^{
        // 追加任务3
        for (int i = 0; i < 2; i++) {
            [NSThread sleepForTimeInterval:2]; // 模拟耗时操作
            NSLog(@"3----%@", [NSThread currentThread]); // 打印当前线程
        }
    });
    
    NSLog(@"asyncSerial--end");

同步+主队列 互等卡住不执行,不会开启新的线程,执行完一个任务,在执行下一个任务

NSLog(@"currentThread---%@", [NSThread currentThread]);
    NSLog(@"syncMain--begin");
    
    dispatch_queue_t queue = dispatch_get_main_queue();
    
    dispatch_sync(queue, ^{
        // 追加任务1
        for (int i = 0; i < 2; i++) {
            [NSThread sleepForTimeInterval:2]; // 模拟耗时操作
            NSLog(@"1----%@", [NSThread currentThread]); // 打印当前线程
        }
    });
    
    dispatch_sync(queue, ^{
        // 追加任务2
        for (int i = 0; i < 2; i++) {
            [NSThread sleepForTimeInterval:2]; // 模拟耗时操作
            NSLog(@"2----%@", [NSThread currentThread]); // 打印当前线程
        }
    });
    
    dispatch_sync(queue, ^{
        // 追加任务3
        for (int i = 0; i < 2; i++) {
            [NSThread sleepForTimeInterval:2]; // 模拟耗时操作
            NSLog(@"3----%@", [NSThread currentThread]); // 打印当前线程
        }
    });
    
    NSLog(@"syncMain--end");

异步+主队列 只在主线程中执行任务,执行完成一个任务,在执行下一个任务

NSLog(@"currentThread---%@", [NSThread currentThread]);
    NSLog(@"asyncMain--begin");
    
    dispatch_queue_t queue = dispatch_get_main_queue();
    
    dispatch_async(queue, ^{
        // 追加任务1
        for (int i = 0; i < 2; i++) {
            [NSThread sleepForTimeInterval:2]; // 模拟耗时操作
            NSLog(@"1----%@", [NSThread currentThread]); // 打印当前线程
        }
    });
    
    dispatch_async(queue, ^{
        // 追加任务2
        for (int i = 0; i < 2; i++) {
            [NSThread sleepForTimeInterval:2]; // 模拟耗时操作
            NSLog(@"2----%@", [NSThread currentThread]); // 打印当前线程
        }
    });
    
    dispatch_async(queue, ^{
        // 追加任务3
        for (int i = 0; i < 2; i++) {
            [NSThread sleepForTimeInterval:2]; // 模拟耗时操作
            NSLog(@"3----%@", [NSThread currentThread]); // 打印当前线程
        }
    });
    
    NSLog(@"asyncMain--end");
  • 通信

线程间通信

// 获取全局并发队列
    dispatch_queue_t queue = dispatch_get_global_queue(DISPATCH_QUEUE_PRIORITY_DEFAULT, 0);
    dispatch_queue_t mainqueue = dispatch_get_main_queue();
    
    dispatch_async(queue, ^{
        // 异步追加任务
        for (int i = 0; i < 2; i++) {
            [NSThread sleepForTimeInterval:2]; // 模拟耗时操作
            NSLog(@"1----%@", [NSThread currentThread]); // 打印当前线程
        }
        // 回到主线程
        dispatch_async(mainqueue, ^{
            // 追加在主线程执行的任务
            [NSThread sleepForTimeInterval:2]; // 模拟耗时操作
            NSLog(@"2----%@", [NSThread currentThread]); // 打印当前线程
        });
    });
    // 可以看到在其他线程中先执行任务,执行完了之后回到主线程执行主线程的相应操作
  • 栅栏

栅栏方法

   dispatch_queue_t queue = dispatch_queue_create("barrier", DISPATCH_QUEUE_CONCURRENT);
    dispatch_async(queue, ^{
        // 追加任务1
        for (int i = 0; i < 2; i++) {
            [NSThread sleepForTimeInterval:2]; // 模拟耗时操作
            NSLog(@"1----%@", [NSThread currentThread]); // 打印当前线程
        }
    });
    
    dispatch_async(queue, ^{
        // 追加任务2
        for (int i = 0; i < 2; i++) {
            [NSThread sleepForTimeInterval:2]; // 模拟耗时操作
            NSLog(@"2----%@", [NSThread currentThread]); // 打印当前线程
        }
    });
    
    dispatch_barrier_async(queue, ^{
        // 追加任务barrier
        for (int i = 0; i < 2; i++) {
            [NSThread sleepForTimeInterval:2]; // 模拟耗时操作
            NSLog(@"barrier----%@", [NSThread currentThread]); // 打印当前线程
        }
    });
    
    dispatch_async(queue, ^{
        // 追加任务3
        for (int i = 0; i < 2; i++) {
            [NSThread sleepForTimeInterval:2]; // 模拟耗时操作
            NSLog(@"3----%@", [NSThread currentThread]); // 打印当前线程
        }
    });
    
    dispatch_async(queue, ^{
        // 追加任务4
        for (int i = 0; i < 2; i++) {
            [NSThread sleepForTimeInterval:2]; // 模拟耗时操作
            NSLog(@"4----%@", [NSThread currentThread]); // 打印当前线程
        }
    });
    // 在执行完栅栏前面的操作之后,才执行栅栏操作,最后在执行栅栏后面的操作
  • 延时执行
NSLog(@"currentThread---%@", [NSThread currentThread]);
    NSLog(@"asyncMain--begin");
    
    dispatch_after(dispatch_time(DISPATCH_TIME_NOW, (int64_t)(20.0*NSEC_PER_SEC)), dispatch_get_main_queue(), ^{
        NSLog(@"after --%@", [NSThread currentThread]);
    });
  • 执行一次
static dispatch_once_t onceToken;
    dispatch_once(&onceToken, ^{
        // 只执行一次,这里默认是线程安全的
    });
  • 快速迭代
dispatch_queue_t queue = dispatch_get_global_queue(DISPATCH_QUEUE_PRIORITY_DEFAULT, 0);
    NSLog(@"apply -- begin");
    dispatch_apply(6, queue, ^(size_t index) {
        NSLog(@"%zd--%@", index, [NSThread currentThread]);
    });
    NSLog(@"apply -- end");

队列组

NSLog(@"currentThread---%@", [NSThread currentThread]);
    NSLog(@"groupNotify--begin");
    
    dispatch_group_t group = dispatch_group_create();
    
    dispatch_group_async(group, dispatch_get_global_queue(DISPATCH_QUEUE_PRIORITY_DEFAULT, 0), ^{
        // 追加任务1
        for (int i = 0; i < 2; i++) {
            [NSThread sleepForTimeInterval:2]; // 模拟耗时操作
            NSLog(@"1----%@", [NSThread currentThread]); // 打印当前线程
        }
    });
    
    dispatch_group_async(group, dispatch_get_global_queue(DISPATCH_QUEUE_PRIORITY_DEFAULT, 0), ^{
        // 追加任务2
        for (int i = 0; i < 2; i++) {
            [NSThread sleepForTimeInterval:2]; // 模拟耗时操作
            NSLog(@"2----%@", [NSThread currentThread]); // 打印当前线程
        }
    });
    dispatch_group_notify(group, dispatch_get_main_queue(), ^{
        // 等前面的异步任务1,2执行完后,回到主线程
        for (int i = 0; i < 2; i++) {
            [NSThread sleepForTimeInterval:2]; // 模拟耗时操作
            NSLog(@"3----%@", [NSThread currentThread]); // 打印当前线程
        }
        NSLog(@"group -- end");
    });
    NSLog(@"我什么时间执行呢");
    // 所有任务都执行完成之后,才执行dispatch_group_notify Block中的任务
 NSLog(@"currentThread---%@", [NSThread currentThread]);
    NSLog(@"groupWait--begin");
    
    dispatch_group_t group = dispatch_group_create();

    dispatch_group_async(group, dispatch_get_global_queue(DISPATCH_QUEUE_PRIORITY_DEFAULT, 0), ^{
        // 追加任务1
        for (int i = 0; i < 2; i++) {
            [NSThread sleepForTimeInterval:2]; // 模拟耗时操作
            NSLog(@"1----%@", [NSThread currentThread]); // 打印当前线程
        }
    });
    
    dispatch_group_async(group, dispatch_get_global_queue(DISPATCH_QUEUE_PRIORITY_DEFAULT, 0), ^{
        // 追加任务2
        for (int i = 0; i < 2; i++) {
            [NSThread sleepForTimeInterval:2]; // 模拟耗时操作
            NSLog(@"2----%@", [NSThread currentThread]); // 打印当前线程
        }
    });
    // 等待上面任务执行完成后,会继续执行下面
    dispatch_group_wait(group, DISPATCH_TIME_FOREVER);
    NSLog(@"groupWait--end");
//   dispatch_group_enter() 标志着一个任务追加到 group,执行一次,相当于 group 中未执行完毕任务数+1
//    dispatch_group_leave() 标志着一个任务离开了 group,执行一次,相当于 group 中未执行完毕任务数-1。
//    当 group 中未执行完毕任务数为0的时候,才会使dispatch_group_wait解除阻塞,以及执行追加到dispatch_group_notify中的任务。
   
   NSLog(@"currentThread---%@", [NSThread currentThread]);
   NSLog(@"groupEnterAndLeave--begin");
   
   dispatch_group_t group = dispatch_group_create();
   dispatch_queue_t queue = dispatch_get_global_queue(DISPATCH_QUEUE_PRIORITY_DEFAULT, 0);
 
   dispatch_group_enter(group);
   dispatch_async(queue, ^{
       // 追加任务1
       for (int i = 0; i < 2; i++) {
           [NSThread sleepForTimeInterval:2]; // 模拟耗时操作
           NSLog(@"1----%@", [NSThread currentThread]); // 打印当前线程
       }
       dispatch_group_leave(group);
   });
   
   dispatch_group_enter(group);
   dispatch_async(queue, ^{
       // 追加任务2
       for (int i = 0; i < 2; i++) {
           [NSThread sleepForTimeInterval:2]; // 模拟耗时操作
           NSLog(@"2----%@", [NSThread currentThread]); // 打印当前线程
       }
       dispatch_group_leave(group);
   });
   
   dispatch_group_notify(group, dispatch_get_main_queue(), ^{
       // 等前面的异步任务1,2执行完后,回到主线程
       for (int i = 0; i < 2; i++) {
           [NSThread sleepForTimeInterval:2]; // 模拟耗时操作
           NSLog(@"3----%@", [NSThread currentThread]); // 打印当前线程
       }
       NSLog(@"group -- end");
   });

相关文章

  • iOS 开发之 GCD 不同场景使用

    iOS 开发之 GCD 不同场景使用 本文在iOS 开发值 GCD 基础 的基础上,继续总结了 GCD 的一些AP...

  • iOS开发多线程之GCD

    iOS开发多线程之GCDiOS开发之GCD同步任务加强iOS开发之GCD串行队列iOS开发之GCD并发队列 GCD...

  • iOS开发之GCD并发队列

    iOS开发多线程之GCDiOS开发之GCD同步任务加强iOS开发之GCD串行队列iOS开发之GCD并发队列 03 ...

  • iOS 开发之 GCD 基础

    iOS 开发之 GCD 基础 本文主要为 GCD 的 队列和执行方法等基础总结,目录如下: [TOC] GCD是什...

  • iOS开发之GCD同步任务加强

    iOS开发多线程之GCDiOS开发之GCD同步任务加强iOS开发之GCD串行队列iOS开发之GCD并发队列 004...

  • iOS开发之GCD串行队列

    iOS开发多线程之GCDiOS开发之GCD同步任务加强iOS开发之GCD串行队列iOS开发之GCD并发队列 实例d...

  • iOS开发之——GCD基础用法

    没有怎么整理看起来有点乱,本文只是介绍GCD的基础用法 任务队列 队列的创建方法/获取方法 创建任务 同步+并发 ...

  • GCD

    iOS多线程 Swift4 GCD深入解析swift GCD 的一些高级用法GCD 之线程组(Dispatch G...

  • 关于GCD常用的方法

    iOS开发多线程篇—GCD的常见用法 一、延迟执行 1.介绍 iOS常见的延时执行有2种方式 (1)...

  • iOS多线程之GCD用法详解

    在上一篇讲解了iOS开发的三种多线程实现方式的特点和用法,在这一篇主要讲解一下GCD的用法。 GCD(Grand ...

网友评论

      本文标题:iOS开发之——GCD基础用法

      本文链接:https://www.haomeiwen.com/subject/kuehsftx.html