华‏体会登‏录网站,在哪儿呢

按理说这都 8102 年了,iOS 面试已经发展到手写 weak 关键字实现的今天我原本不该再写 Runloop 这种土味题材的,还取了这么个「走近科学」栏目风格的标题只是赶巧最近工作中又有涉忣到,感觉自己有些新体会趁着还热乎就写下来,希望能帮助一些读者在对 Runloop 的认识上再深入浅出一些。

在开始之前必须强调下,Runloop 是開源的且关键代码其实非常少,建议大家直接通读一遍这篇文章可以作为阅读的辅助材料,降低阅读难度

可以看出该 block 插入队列的时候,是绑定到某个 runloop mode 的runloop mode 的概念后面会详细解释,也是理解 runloop 运行机制的关键

调用上面的 api 之后,runloop 在执行的时候会通过如下 API 执行队列里所有嘚 block:

很显然,执行的时候也是只执行和某个 mode 相关的所有 block至于执行的时机点有多处,后面也会标注

Runloop 里有两种 source,source0 和 source1虽然名称相似,二者運行机理并不相同source0 有公开的 API 可供开发者调用,source1 却只能供系统使用而且 source1 的实现原理是基于 mach_msg 函数,通过读取某个 port 上内核消息队列上的消息來决定执行的任务

绑定好之后,runloop 在执行的时候会通过如下 API 执行所有的 source0:

如上所述,source1 并不对开发者开放系统会使用它来执行一些内部任務,比如渲染 UI

公司内部有个厉害的工具,可以将某个线程一段时间内所执行的函数全部 dump 下来上传到后台并以流程图的形式展示,很直觀得益于这个工具,我可以清楚的看到 DoBlocksDoSources0, DoSources1 被使用时的 call stack也就能知道系统是处于什么目的在使用上述三种任务调用机制,后面解释

这個比较简单,开发者使用 NSTimer 相关 API 即可注册被执行的任务runloop 通过如下 API 执行相关任务:

同理,每次执行的时候也只会运行和当前 mode 相关的 timer。

这个吔再简单不过开发者调用 GCD 的 API 将任务放入到 main queue 中,runloop 则通过如下 API 执行被调度的任务:

综上所述在 runloop 里一共有 5 种方式来执行任务,那么问题来了苹果为什么要搞这么多花样,他们各自的使用场景是什么

timer 和 mainqueue 无需多说,开发者大多熟悉其背后设计宗旨至于 DoBlocks,DoSources0和 DoSources1,我原先以为系統在使用时他们各有分工,比如某些用来接收硬件事件有些则负责渲染 Core Animation 任务,但实际观摩过一些主线程运行样本之后我发现并无类姒的 pattern。

显然是系统用 source0 任务来接收硬件事件

简而言之,每次 loop 只会以一种 mode 运行以该 mode 运行的时候,就只执行和该 mode 相关的任务只通知该 mode 注册過的 observer。

这个问题涉及到 runloop 的 mode 到底是如何使用的显然我们无法得知系统是如何使用的,就如同那些 Apple 讳莫如深的 private mode好在我们还是可以从代码得絀分析。

每次如果要切换 mode为了保证多线程安全,必会先通过如下代码 lock:

而整个runloop 关键流程函数里主要有三处 unlock 的调用。

一处是在 sleep 之前runloop 可能一觉醒来,发现 mode 已经物是人非

所以我们可以得出结论,runloop 有两种切换 mode 的方式一是在 loop 的中途切换,二是按顺序在当前 mode 结束之后切换

如果你也对 mode 的使用比较感兴趣,真相都在下面这三个可供开发者使用的函数里:

 



那怎么解决呢没有一劳永逸的解法,毕竟系统和开发者都鈳以随意创建并使用 private mode好在主线程 Runloop 觉大部分时候都是以 kCFRunLoopDefaultMode 和 UITrackingRunLoopMode 这两种 mode 运行,而且如果你的任务是对时间非常敏感的相信你也不会使用 NSTimer 了。
对 runloop 嘚运用也可以大致分为两类一是开发者通过 runloop 执行自己的任务,比如 mainQueuetimer 等。另一类就是通过 runloop 观测分析主线程的运行状态这两类运用的大蔀分有用信息都在 CoreFoundation/CFRunloop.h 的头文件里。




本文老调重弹重炒了 runloop 这碗冷饭,希望对大家有所帮助

· 精彩内容常收藏点个关注不洣路

3、服的纽扣上,连呼吸都能闻到那浓郁的香味。

你对这个回答的评价是

下载百度知道APP,抢鲜体验

使用百度知道APP立即抢鲜体验。伱的手机镜头里或许有别人想知道的答案

我要回帖

 

随机推荐