GCD 是苹果APP开发(Objective-c)中管理线程的一种方式!
涉及到线程 就有两个很重要的概念 任务 和 队列
任务: 任务就是需要执行的一项操作 在执行操作的时候又 可以分为 同步和异步执行方式!
--- 同步执行: 不开辟新的线程,就占用当前的线程 来执行这项任务 (不具备开辟新线程的能力)!
--- 异步执行: 在和当前线程 不同的另一个线程中执行任务 (具有开辟新线程的能力)!
队列 : 这里的队列是指任务队列,遵守FIFO ( first in first out)特性! 队列有两种类型 串行队列 和 并行队列
--- 串行队列 : 单通道(好比只有一条水管流水),一个接一个的执行队列中任务!
执行特点:在 全部并发队列、手工创建串行队列、主队列 中都没有开启新线程,串行特性执行任务!
--- 并行队列 :多通道 (好比,有多个水管同时流水),多个任务可以同时执行(多个水管中的水可以同时流出)!
执行特点: 在全局并发队列 中有开启了新的线程并行执行任务
在自己创建的队列中 有开启新线程 串行特性执行任务
在主队列中 没有开启新线程 串行特性执行任务
GCD 使用步骤 :
1.明确定制任务,根据任务的特点 (同步还是异步) 选择 合适的队列类型(串行还是并行)!
2. 将任务加入到多列之中!
3.系统根据任务类型 或者开新线程 或者不开新线程 、根据 队列类型 来取出一个任务或者多个任务开始执行!
同步函数和异步函数
dispatch_sync(queue, ^{
NSLog(@"同步函数");
});
dispatch_async(queue, ^{
NSLog(@"异步函数");
});
获取几种队列 :
//主队列
dispatch_queue_t mainQueue = dispatch_get_main_queue();
// 串行队列
dispatch_queue_t queue = dispatch_queue_create("queueName", DISPATCH_QUEUE_SERIAL);
// 并行队列
dispatch_queue_t queue1 = dispatch_queue_create("queueName", DISPATCH_QUEUE_CONCURRENT);
//全部并发队列
dispatch_queue_t queue2 = dispatch_get_global_queue(DISPATCH_QUEUE_PRIORITY_DEFAULT, 0);
几种任务和队列的配合方式:
//1.同步函数 + 串行队列
// 串行队列
dispatch_queue_t queue = dispatch_queue_create("queueName", DISPATCH_QUEUE_SERIAL);
dispatch_sync(queue, ^{
NSLog(@"同步函数 + 串行队列");
});
//2.异步函数 + 串行队列
// 串行队列
dispatch_queue_t queue = dispatch_queue_create("queueName", DISPATCH_QUEUE_SERIAL);
dispatch_async(queue, ^{
NSLog(@"异步函数 + 串行队列");
});
//3.同步函数 + 并行队列
// 串行队列
dispatch_queue_t queue = dispatch_queue_create("queueName", DISPATCH_QUEUE_CONCURRENT);
dispatch_sync(queue, ^{
NSLog(@"同步函数 + 并行队列");
});
//4.异步函数 + 并行队列
// 串行队列
dispatch_queue_t queue = dispatch_queue_create("queueName", DISPATCH_QUEUE_CONCURRENT);
dispatch_async(queue, ^{
NSLog(@"异步函数 + 并行队列");
});
//主队列
dispatch_queue_t mainQueue = dispatch_get_main_queue();
dispatch_async(mainQueue, ^{
NSLog(@"主队列 + 异步函数");
});
dispatch_sync(mainQueue, ^{
NSLog(@"主队列 + 同步函数");
});
//全局并发队列 + 同步函数 实现线程依赖一次执行
dispatch_queue_t queue = dispatch_get_global_queue(DISPATCH_QUEUE_PRIORITY_DEFAULT, 0);
for (int i = 0; i < 5; i++) {
dispatch_sync(queue, ^{
NSLog(@"for -- 1 -- %d",i);
});
}
for (int i = 0; i < 5; i++) {
dispatch_sync(queue, ^{
NSLog(@"for -- 2 -- %d",i);
});
}
结果:
for -- 1 -- 0
for -- 1 -- 1
for -- 1 -- 2
for -- 1 -- 3
for -- 1 -- 4
for -- 2 -- 0
for -- 2 -- 1
for -- 2 -- 2
for -- 2 -- 3
for -- 2 -- 4
//全局并发队列 + 异步函数 开启新线程并发执行
dispatch_queue_t queue = dispatch_get_global_queue(DISPATCH_QUEUE_PRIORITY_DEFAULT, 0);
for (int i = 0; i < 5; i++) {
dispatch_async(queue, ^{
NSLog(@"for -- 1 -- %d",i);
});
}
for (int i = 0; i < 5; i++) {
dispatch_async(queue, ^{
NSLog(@"for -- 2 -- %d",i);
});
}
结果:
** for -- 1 -- 1**
** for -- 1 -- 0**
** for -- 1 -- 2**
** for -- 1 -- 3**
** for -- 1 -- 4**
** for -- 2 -- 0**
** for -- 2 -- 1**
** for -- 2 -- 2**
** for -- 2 -- 3**
回主线程 (用于更新UI)
dispatch_async(dispatch_get_main_queue(), ^{ NSLog(@"%@",[NSThread currentThread]); });
延时执行
dispatch_after(dispatch_time(DISPATCH_TIME_NOW, (int64_t)(1.5 * NSEC_PER_SEC)), dispatch_get_main_queue(), ^{
NSLog(@"1.5s后执行内容");
});
单利模式用到的一次性
static dispatch_once_t onceToken;
dispatch_once(&onceToken, ^{
// 只执行1次的代码(这里面默认是线程安全的
)});
网友评论