RunLoop详解及相关问题

最近整理了些RunLoop相关知识,整理如下:

RunLoop:是运行循环,其实就是不停地跑圈。

一、RunLoop的作用:

1.保持程序的持续运行

2.处理App中的各种事件(如:触摸事件,定时器事件,Selector事件)

3.节省CPU资源,提高程序性能,该做事情的时做事情,该休息时休息。

4.……

RunLoop详解及相关问题_第1张图片
没有RunLoop
RunLoop详解及相关问题_第2张图片
有RunLoop情况
RunLoop详解及相关问题_第3张图片
main函数的RunLoop

二、RunLoop对象

在iOS中有两套API来访问和使用RunLoop

第一种是:Foundation框架中的NSRunLoop对象

第二种是:Core Foundation框架中的CFRunLoopRef对象

两者都代表着RunLoop的对象

NSRunLoop是基于CFRunLoopRef的一层OC包装,所以你要了解RunLoop内部结构需要多研究研究CFRunLoopRef层面的API(即CoreFoundation框架API)

三、RunLoop对象与线程的关系

每条线程都有唯一的一个与之对应的RunLoop对象

主线程的RunLoop已经自动创建好了,子线程的RunLoop需要手动去创建

RunLoop在第一次获取的时候创建,在线程结束的时候销毁

三、如何获取当前线程和主线程

1、Foundation框架中的获取方法:

[NSRunLoop      currentRunLoop];// 获得当前线程的RunLoop对象

[NSRunLoop      mainRunLoop];// 获得主线程的RunLoop对象

2/CoreFoundation框架中的获取方法:

CFRunLoopGetCurrent();// 获得当前线程的RunLoop对象

CFRunLoopGetMain();// 获得主线程的RunLoop对象

四、CoreFoundation框架中RunLoop的相关类(5个类)

1、CFRunLoopRef

2、CFRunLoopModeRef   

3、CFRunLoopSourceRef

4、CFRunLoopTimerRef

5、CFRunLoopObserverRef

解释这5个相关类别:

lCFRunLoopModeRef代表RunLoop的运行模式

一个RunLoop包含若干个Mode,每个Mode又包含若干个Source/Timer/Observer

每次RunLoop启动时,只能指定其中一个Mode,这个Mode被称作CurrentMode

如果需要切换Mode,只能退出Loop,再重新指定一个Mode进入

这样做主要是为了分隔开不同组的Source/Timer/Observer,让其互不影响

系统默认注册了5个Mode:

kCFRunLoopDefaultMode:App的默认Mode,通常主线程是在这个Mode下运行

UITrackingRunLoopMode:界面跟踪Mode,用于ScrollView追踪触摸滑动,保证界面滑动时不受其他Mode影响

UIInitializationRunLoopMode:在刚启动App时第进入的第一个Mode,启动完成后就不再使用

GSEventReceiveRunLoopMode:接受系统事件的内部Mode,通常用不到

kCFRunLoopCommonModes:这是一个占位用的Mode,不是一种真正的Mode

CFRunLoopSourceRef是事件源(输入源)

l以前的分法

                    Port-Based   Sources

                    Custom Input   Sources

                    Cocoa Perform   Selector Sources

现在的分法

                        Source0:非基于Port的

                        Source1:基于Port的

CFRunLoopTimerRef是基于时间的触发器

基本上说的就是NSTimer

�CFRunLoopObserverRef是观察者,能够监听RunLoop的状态改变

可以监听的时间点有以下几个

RunLoop详解及相关问题_第4张图片
时间点

五、RunLoop处理逻辑-官方文档

RunLoop详解及相关问题_第5张图片
官方1
RunLoop详解及相关问题_第6张图片
官方2
RunLoop详解及相关问题_第7张图片
大牛

六、应用:

NSTimer

ImageView显示

PerformSelector

常驻线程

自动释放池

七、面试题:

1、什么是RunLoop?

从字面意思上看就是运行循环,其实它内部就是do-while循环,在这个循环内部不断地处理各种事件(比如:Source,timer,Observer)

一个线程对应一个RunLoop,主线程的RunLoop默认是开启的,子线程的RunLoop需要手动开启。(其实就是调用run方法)

RunLoop只能选择一个Mode启动,如果当前Mode中没有任何的Source,Timer,Observer,那么就直接退出RunLoop。

2、你在开发过程中如何使用RunLoop?什么应用场景?

A、开启一个常驻线程(让一个子线程不进入消亡状态,等待其他线程发来消息,处理其他事件)

在一个子线程开启一个定时器;

在子线程中进行一些长期监控

B、可以控制定时器在特种模式下执行

C、可以让某些事件(行为任务)在特定模式下执行

D、可以添加Observer监听RunLoop的状态,比如监听点击事件的处理,在点击事件之前做一些事情。

3、自动释放池什么时候释放?

在RunLoop睡眠之前释放(kCFRunLoopBeforeWaiting)

八、学习链接和资料

苹果官方文档1

CFRunLoopRef是开源框架

欢迎关注本人的公众号之后会有更多iOS相关知识与视频,希望大家多多指教与交流

欢迎骚扰!!!

RunLoop详解及相关问题_第8张图片
个人公众号

你可能感兴趣的:(RunLoop详解及相关问题)