initialize方法解析
2019-08-21 本文已影响0人
南城同學
-
+initialize
方法会在类第一次接收到消息时调用;
调用顺序:
- 先调用父类的
+initialize
,再调用子类的。(先初始化父类,再初始化子类,每个类只会初始化1次。)
void _class_initialize(Class cls)
{
xxxxxxxxx
//又是一个递归,如果有父类,且父类没有初始化,就先初始化父类,
supercls = cls->superclass;
if (supercls && !supercls->isInitialized()) {
_class_initialize(supercls);
}
xxxxxxx
callInitialize(cls);
}
void callInitialize(Class cls)
{
//初始化时,发送一个"initialize" 方法消息。
((void(*)(Class, SEL))objc_msgSend)(cls, SEL_initialize);
asm("");
}
可以抽减成如下模型:
if (!sutdentInitialized) {
if (!personInitialized) {
objc_msgSend([Person class], @selector(initialize));
personInitialized = YES;
}
objc_msgSend([Student class], @selector(initialize));
sutdentInitialized = YES;
}
+initialize
方法不同于+load
的地方:
-
+initialize
是通过objc_msgSend
进行调用的; - 如果分类实现了
+initialize
,就覆盖类本身的+initialize
调用。(找到就不再找了) - 如果子类没有实现
+initialize
,会调用父类的+initialize
。(所以父类的+initialize
可能会被调用多次。)