load和initialize常常被说起,但实际编码中其实使用很少,一个知识即便当时了解的再清楚,一直不使用,也会慢慢忘记,就好像我如今想不起来高中物理的不少公式同样。函数
提及这些总要提及原理,其实原理是什么呢,就是苹果在runtime的源码中怎样去调用这两个方法的。细节不少,挑出关键流程其实也只能是知其然不知其因此然,只能是知道了这么作,殊不知道为何这么作。优秀的源码老是通过屡次测试屡次修改屡次优化的。测试
站在路的终点,咱们可能很难想起走在途中的心路历程。仍是须要慢慢摸索,认真沉淀才行。优化
放个总结,方便回忆。ui
维度 | load | initialize |
---|---|---|
是否须要调用Super | 不须要 | 不须要 |
调用时机 | 类或者category加载到runtime时由系统自动调用 在main函数以前 | 在类或者子类在第一次收到消息时调用(类消息或者实例消息)在main函数以后 |
调用方式 | 直接经过函数的内存地址调用的,不走msg_send,不走OC消息转发,每一个类的load方法都是独立的 | 走OC消息转发, msg_send |
调用次数 | 只会调用一次 | 1. 可能会调用屡次,若是子类没有实现该方法,则子类在第一次收到消息时会调用父类的方法。2.若是在子类收到消息前,父类没有收到过消息,那么会先调用父类的initialize方法以后再调用子类的initialize方法。 |
调用顺序 | 父类-子类-category 。1.全部的类都加载完以后才会调用全部的category。 2.不一样的类的load执行顺序跟编译顺序有关,能够在Target -> Build Phases -> Compile Sources 中调整顺序。但全部的category都是在全部的类的load都执行完以后,才会调的。 3.多个类的多个category或者一个类的不一样category的load方法的顺序一样跟编译顺序有关,能够在compiles source中调整。 | 父类-子类(若是category有实现,会只调用category中的实现;父类的category会覆盖父类的实现,子类的category会覆盖子类的category实现) |
使用 | 通常用来实现 Method Swizzle | 通常用来初始化全局变量 或者 静态变量 |