APP 启动过程
1.解析 plist 文件,创建沙盒, 检查权限
2.加载 Mach-O 文件
3.加载动态连接器(dylb)
4.dylb 加载动态链接库(dylib,tbd)
5.进行 rebase (指针调整, ASLR 保证偏移地址的安全性)
6.进行 bind(符号绑定,例如NSLog方法,在编译时期生成的mach-o文件中,会创建一个符号,绑定就是给符号赋值的过程)
7.Objc runtime 的初始化(Objc class ,分类的注册加载,selector唯一性检查等)
8.Initializers(初始化,C++静态对象加载, 加载 +load 方法等)
9.dylb调用 mian 函数
10.调用UIApplicationMain
11.调用applicationWillFinishLaunching
12.调用didFinishLaunchingWithOptions
APP 启动优化
pre-mian 阶段
1.加载 Dylib
尽量少的使用自定义的动态库,或者考虑合并多个动态库,其中一个建议是当大于6个的时候,则需要考虑合并它们2.Rebase/Binding
减少App的Objective-C类,分类和Selector的个数。这样做主要是为了加快程序的整个动态链接, 在进行动态库的重定位和绑定(Rebase/binding)过程中减少指针修正的使用,加快程序机器码的生成;3.Objc setup
大部分ObjC初始化工作已经在Rebase/Bind阶段做完了,这一步dyld会注册所有声明过的ObjC类,将分类插入到类的方法列表里,再检查每个selector的唯一性。
在这一步倒没什么优化可做的,Rebase/Bind阶段优化好了,这一步的耗时也会减少。-
- Initializers
到了这一阶段,dyld开始运行程序的初始化函数,调用每个Objc类和分类的+load方法,调用C/C++ 中的构造器函数(用attribute((constructor))修饰的函数),和创建非基本类型的C++静态全局变量。Initializers阶段执行完后,dyld开始调用main()函数。
在这一步,我们可以做的优化有:
- 减少在类的+load方法里做事情,尽量把这些事情推迟到+initiailize
- 减少C++静态全局变量的个数
- Initializers
main 阶段
- 1.didFinishLaunchingWithOptions 里面减少耗时或者多余的操作
- 2.梳理业务逻辑,把可以延迟执行的逻辑做延迟执行处理
- 3.避免在首页控制器的viewDidLoad和viewWillAppear做太多事情