多线程

2021-04-11  本文已影响0人  顺其自然2017

一、Grand Central Dispatch(GCD )

GCD 是苹果开发的一个多核编程的方法,采用了线程池模式,支持多核处理器

优点:

1、GCD 可用于多核的并行运算;

2、GCD 会自动利用更多的 CPU 内核(比如双核、四核);

3、GCD 会自动管理线程的生命周期(创建线程、调度任务、销毁线程);

可实现的功能:

1、多任务并行执行

2、计时器&延时执行

3、多任务之间依赖执行

队列(FIFO):串行队列  并行队列,存放将要执行的任务。串行队列只有一个线程,所有任务在这一个线程中顺序执行;并行队列可以有多个线程,所有任务可以在不同线程同时执行

执行:异步执行和同步执行,异步执行后需任务无需等待上一个任务执行完毕,可以直接开启其他开启新线程执行;同步执行,等待上一个任务执行完毕后才开始执行;同步/异步决定是否开启新线程,串行/并行决定开启新线程数量

多线程:并行队列+异步执行,多线程最大并发量可以通过信号量控制

获取队列 

// 串行队列的创建方法

dispatch_queue_t queue = dispatch_queue_create("队列名称标识", DISPATCH_QUEUE_SERIAL);

// 并发队列的创建方法

dispatch_queue_t queue = dispatch_queue_create("队列名称标识", DISPATCH_QUEUE_CONCURRENT);

//获取主队列 ->串行队列

dispatch_get_main_queue()

//获取全局队列-> 并行队列

dispatch_queue_t queue = dispatch_get_global_queue(DISPATCH_QUEUE_PRIORITY_DEFAULT, 0);

添加任务

异步添加任务

dispatch_async(queue, ^{

});

同步添加任务

dispatch_sync(queue, ^{

});

GCD之间的通信:异步添加任务到其他线程

其他方法 

栅栏方法:dispatch_barrier_async(queue, ^{ });

  同一队列中,等待栅栏函数前的任务完成才会执行栅栏内任务,最后回复继续执行原流程

延时方法:dispatch_after(timer, queue, ^{ });

timer 是dispatch_time_t类型,dispatch_time(计时开始时间, 延迟时间);

只是在时间节点将任务添加到队列中,准备执行,时间上不准确

一次执行:dispatch_once(dispatch_once_t,^{});  

保证线程安全,常用来实现单例

迭代方法: dispatch_apply(count, queue, ^(size_t index) { });

异步执行count次数迭代方法,无先后顺序,

队列组 dispatch_group

创建队列组: dispatch_group_create();

添加任务标识:dispatch_group_enter(group)

移除任务标识:dispatch_group_leave(group)

追加任务:dispatch_group_async(group, dispatch_get_global_queue(DISPATCH_QUEUE_PRIORITY_DEFAULT, 0), ^{});

group中任务完成后通知添加指定执行任务:dispatch_group_notify(group, dispatch_get_main_queue(), ^{ }); 异步操作不会阻塞当前线程

等待group中任务完成后继续在当前线程执行后续任务:dispatch_group_wait(group, DISPATCH_TIME_FOREVER); 会阻塞当前线程

信号量 dispatch_semaphore

三种用途:

1、控制并行队列线程并发数

2、保持线程同步,将异步执行任务转换为同步执行任务

3、保证线程安全,为线程加锁

创建信号量:dispatch_semaphore_create(count); count 信号量个数

占用信号量: dispatch_semaphore_wait(semaphore, DISPATCH_TIME_FOREVER);

释放信号量:dispatch_semaphore_signal(semaphore);

计时器实现:dispatch_source_t

创建计时器:dispatch_source_create(DISPATCH_SOURCE_TYPE_TIMER,0,0,queue);

设置计时器:dispatch_source_set_timer(timer,dispatch_walltime(nil,0),10*NSEC_PER_MSEC,0);

设置操作事件:dispatch_source_set_event_handler(timer,^{});

开始:dispatch_resume(timer);

暂停:dispatch_suspend(timer);

取消:dispatch_source_cancel(timer); 只能取消尚未执行的任务

上一篇下一篇

猜你喜欢

热点阅读