这篇文章写的是看完 WWDC 17 - Modernizing GCD Usage 之后的笔记。

一、Parallelism & Concurrency

Parallelism 指的是在多个 CPU 核上同时跑代码。

DispatchQueue.concurrentPerform(iterations: 100) { (i) in
print("\(i)")
}

为了更好的利用多个 CPU 的优势,把任务分为尽可能多的部分,方便调度。
如果只有 3 个部分,那么很可能会出现 Bubble,即有时间片没有被利用。

Concurrency 即我们通常说的多任务,这个 session 讲的也大部分是 Concurrency。

二、Context Switching

上下文切换是 Concurrency 可以实现的基础,但是过多的上下文切换会带来性能问题。

2.1 重复的获取互斥资源引发的等待

每次切换需要 10μs 的量级

可以考虑用 un_fair_lock 来解决。
先来看 fair_lock。多个线程同时竞争这个锁得时候, 会考虑公平性尽可能的让不同的线程公平。 这个公平其实是有很大的性能损失换来的。

在上面的图中,锁先被线程 1 持有,然后释放,被线程 2 持有,引起一次上下文切换。

而在非公平锁中,线程 1 释放锁之后,马上又获得了锁,没有造成上下文切换。

可以用 Instrument 发现问题,然后选择适当的锁。

2.2 重复地在不同的操作 (operations)中切换

一个例子是有很多网络连接,而每一个连接都对应一个串行队列。当网络发生变化时,这些队列中的代码都要被执行。
假如队列形式如下,S 表示网络发生变化, Q 表示网络变化时代码要执行的串行队列。

当网络变化时,会有 3 个队列生成,对应三个线程。

显然会发生上下文切换。

如果我们指定 3 个队列的 target 是同一个 queue,如下图:

那么在网络发生变化时,这三个队列的代码将在同一个 queue 中执行,不会有上下文切换。

此外,如果把太多的任务加到全局并行队列,也会导致生成太多线程。

• If workitems block, more threads will be created
• May lead to thread explosion

苹果推荐的方法是,每一个子系统(数据库、网络。。。)有一个队列层级,如下图:

三、统一队列标识符 (Unified Queue Identity)

具体原理没有看明白,大概是每一个队列都在内核中有一个标志符,可以根据这个标识符做优化。
在之前,把两个 source 的队列设置为一个,当处理 S1 时, S2 被触发,那么会新建一个线程。

经过优化之后,不会创建一个额外的线程了。
大致原理是当 S2 触发时,系统知道对应的队列正在执行,于是做了一个标记。
当处理完毕之后,再进行相应处理。

四、如何处理代码

4.1 在 activation 之后不要改变 dispatch object

即在 activate 函数调用之后,不要改变 source handler 和 target queue。因为系统会创建一个快照,根据这个快照来优化调度。

let mySource = DispatchSource.makeReadSource(fileDescriptor: fd, queue: myQueue)
mySource.setEventHandler(qos: .userInteractive) { … }
mySource.setCancelHandler { close(fd) }
mySource.activate()
mySource.setTarget(queue: otherQueue)//wrong!!!!!!!!!!!!!!!!

4.2 保护好队列的层级

使用新的函数,在创建队列时指定 target queue。

Q1 = dispatch_queue_create_with_target("Q1", DISPATCH_QUEUE_SERIAL, EQ)
//下面被淘汰啦
Q1 = dispatch_queue_create("Q1",DISPATCH_QUEUE_SERIAL)
dispatch_set_target_queue(Q1, EQ)

4.3 使用新的工具

Instrument 带有 GCDPerformance 工具,可以诊断问题。

五、参考

GCD 使用若干注意事项的更多相关文章

  1. WPF:自动执行"机器人"程序若干注意事项

    企业应用中,经常会遇到一些需要定时自动执行的程序来完成某些功能,比如:自动定时从第三方web service取回数据.定时对历史数据进行清理.定时向ftp上传业务数据... 这类程序,我习惯称为“机器 ...

  2. 解决Bootstrap 附加导航(Affix)的问题和使用时若干注意事项

    1.要清楚Affix分别赋予的class, 开始:affix-top 达到top参数:affix 达到bottom参数:affix-bottom 2.一定要自定义这些class,否则 插件会默认给你在 ...

  3. 制作C/C++动态链接库(dll)若干注意事项

    一.C\C++ 运行时库编译选项简单说明 问题:我的dll别人没法用 运行时库是个很复杂的东西,作为开发过程中dll制作需要了解的一部分,这里主要简单介绍一下如何选择编译选项. 在我们的开发过程中时常 ...

  4. Oracle EBS Form 发布到Server端的注意事项

    前段时间在本地XP系统上测试了一些整合javabean的Form例子,想着发布到服务器段去看看能否运行正常,一开始以为会和本地XP系统一样,部署到相关的目录下进行一些配置就可以了,但实际过程却和想象的 ...

  5. iOS面试题大全-点亮你iOS技能树

    所有的内容大部分来自于网络的搜集,所以我不是一个创造者,而是一个搬运工.我尽量把题目,尤其是参考答案的出处列明.若有任何疑问,建议,意见,请联系我. 第一部分面试题来源于iOS-Developer-I ...

  6. iOS面试题

    一个区分度很大的面试题 考察一个面试者基础咋样,基本上问一个 @property 就够了: @property 后面可以有哪些修饰符? 线程安全的: atomic,nonatomic 访问权限的 re ...

  7. python之路四

    内建函数 内建函数详解: 1. abs(x) abs()函数返回数字(可为普通型.长整型或浮点型)的绝对值.如果给出复数,返回值就是该复数的模.例如: >>>print abs(-2 ...

  8. 李洪强iOS经典面试题下

    李洪强iOS经典面试题下 21. 下面的代码输出什么? @implementation Son : Father - (id)init { self = [super init]; if (self) ...

  9. 招聘一个靠谱的 iOS

    近一年内陆续面试了不少人了,从面试者到面试官的转变让我对 iOS 招聘有了更多的感受.经过了前段时间的一大波面试,我们终于找到了志同道合的小伙伴,面试也暂时告一段落了.总结下面试人过程中的感受,你也可 ...

随机推荐

  1. Python any() 函数

    Python any() 函数  Python 内置函数 描述 any() 函数用于判断给定的可迭代参数 iterable 是否全部为 False,则返回 False,如果有一个为 True,则返回 ...

  2. animate.css动画种类

    animate.css 一个非常好用的css动画库 Github地址 包括了一下多种动画 1. bounce 弹跳 2. flash 闪烁 3. pulse 放大,缩小 4. rubberBand 放 ...

  3. abp AutoMap Custom Mapping

    [DependsOn(typeof(AbpAutoMapperModule))] public class MyModule : AbpModule { public override void Pr ...

  4. 看图说说Heap中对象的生存状态

  5. JAVA反射机制o

    Reflection是Java 程序开发语言的特征之一,它允许运行中的 Java 程序对自身进行检查,或者说"自审",并能直接操作程序的内部属性.例如,使用它能获得 Java 类中 ...

  6. Ubuntu的常识使用了解4

    寻找文件的「名称」 在Linux系统当中,文件的数量非常非常的多, 需要使用查找工具来高效查找指定文件位置:

  7. 浅析互联网系统和传统企业IT系统的异同

    前不久,一则中行宕机的消息引起了网上IT人士的热议.其中对于大型机或者RISC系统的稳定性可靠性的质疑更是热议中的主流声音,很多人拿现在互联网系统做对比,认为大型机所谓的几个9都是吹出来的云云.在这里 ...

  8. 企业搜索引擎开发之连接器connector(二十八)

    通常一个SnapshotRepository仓库对象对应一个DocumentSnapshotRepositoryMonitor监视器对象,同时也对应一个快照存储器对象,它们的关联是通过监视器管理对象D ...

  9. handsontable-mobiles

    适配移动端:文档不完整,现在只能适配ipad4

  10. 编译语言 vs 解释语言

    编译语言 vs 解释语言 阅读:  评论:  作者:Rybby  日期:  来源:rybby.com 一直以为,编译语言的性能绝对比解释语言快,因为就理论而言,解释语言要一边解释(将脚本语言翻译成计算 ...