GCD5: 用GCD同步执行非UI相关的任务

讨论:

  当执行那些与 UI 无关的任务,或者与 UI 交互的任务时,和执行其他任务一样,会需要大量时间,以上情况会经常出现。例如,你想下载一个图片并想在下载完成之后展现给用户。下载过程却和 UI 没有任何关系。 
  对于任何与 UI 无关的任务,你可以使用 GCD 中的全局并发队列。它们允许同步和异步执行。 
  如果你同步提交一个任务到一个并发队列,同时提交另一个同步任务到另一个并发队列;相对而言这两个同步任务将异步运行,因为他们运行在两个不同的并发队列上。理解这一点很重要,正如我们将看到的那样,你想确定在 B 任务开始之前 A 任务完成了。为了保证这一点,把它们同时提交一个相同的队列。 

下面我们看个例子:

它输出整数 1 到 1000 两次,一个完整的序列紧跟着另一个,但是并不会阻止主线。我们可以创建一个为我们计数的Block并且把同一个Block调用两次: 
void(^printFrom1To100)(void) = ^{
    NSUInteger counter = 0;
    for(counter = 1;counter <= 100;counter++){
        NSLog(@"Counter = %lu - Thread = %@", (unsigned long)counter,
              [NSThread currentThread]);
    }
};
现在我们用 GCD 来调用这个 Block :
   dispatch_queue_t concurrentQueue = dispatch_get_global_queue(DISPATCH_QUEUE_PRIORITY_DEFAULT, 0);
//priority 优先级
    dispatch_sync(concurrentQueue, printFrom1To100);
    dispatch_sync(concurrentQueue, printFrom1To100);
运行这段代码,你会发现计数发生在主线程,即使你已经要求过并发队列执行这个任务。 

为什么呢?:这是 GCD 的优化。 作为一个优化,这个函数调在可能的情况下在当前线程上调用了Block。

 执行时为了在一个分派队列上用 C 函数来同步代替 Block Object,使用 dispatch_sync_f function:

void printFrom1To1002(void *paramContext){
    NSUInteger counter = 0;
    for(counter = 1;counter <= 100;counter++){
        NSLog(@"Counter = %lu - Thread = %@", (unsigned long)counter,
              [NSThread currentThread]);
    }
}
//调用
dispatch_sync_f(concurrentQueue, NULL, printFrom1To1002);
Dispatch_get_global_queue 函数的第一个参数说明了并发队列的优先级,这个属性 GCD 必须替程序员检索。优先级越高,将提供更多的 CPU Timeslice 来获取该队列执行的代码。
 
你可以使用下面这些值作为 Dispatch_get_global_queue 函数的第一个参数: 

 DISPATCH_QUEUE_PRIORITY_LOW         您的任务比正常任务用到更少的时间片。 

DISPATCH_QUEUE_PRIORITY_DEFAULT    执行代码的默认系统优先级将应用于您的任务。

DISPATCH_QUEUE_PRIORITY_HIGH          和正常任务相比,更多的时间片会应用到你的任务中。

Dispatch_get_global_queue 函数的第二个参数是预留的,你只要一直给它输入数值 0 就可以了。 

priority  [praɪ'ɒrɪtɪ] n. [通信][计]优先;优先权

原文地址:https://www.cnblogs.com/safiri/p/4063280.html