OC中l(wèi)oad 和initialize 的區(qū)別

OC文件在編譯后赡鲜,類相關(guān)的數(shù)據(jù)結(jié)構(gòu)會(huì)保留在目標(biāo)文件中,在運(yùn)行時(shí)得到解析和使用氮帐。在應(yīng)用程序運(yùn)行起來(lái)的時(shí)候隘截,類的信息會(huì)有加載和初始化過(guò)程扎阶,這個(gè)過(guò)程就涉及到了類的兩個(gè)類方法:loadinitialize。下面我們就來(lái)介紹一下這2個(gè)方法的區(qū)別婶芭。

1.load方法

1.1 調(diào)用時(shí)機(jī)

啟動(dòng)程序時(shí)东臀,參與編譯的類、分類會(huì)被加載進(jìn)內(nèi)存雕擂,load 方法就是在類被加載的時(shí)候調(diào)用的(前提是這個(gè)類有實(shí)現(xiàn)load方法)啡邑。

該方法的調(diào)用和這個(gè)類是否被使用無(wú)關(guān)贱勃,即使一個(gè)類在整個(gè)程序中都沒(méi)有用到井赌,也沒(méi)有任何一個(gè)文件去引用該類的頭文件谤逼,該類的load方法一樣會(huì)被調(diào)用。

等所有類仇穗、分類都加載進(jìn)內(nèi)存后才會(huì)調(diào)用程序的main函數(shù)流部,所以所有類的load方法都是在main函數(shù)之前被調(diào)用的。而且每個(gè)類纹坐、分類的load方法都只會(huì)被調(diào)用一次

1.2 調(diào)用順序

一個(gè)城西中如果所有的類枝冀、分類都實(shí)現(xiàn)了load方法,那么所有的load方法都會(huì)被調(diào)用耘子。他們的執(zhí)行順序遵循以下規(guī)則:

  • 先執(zhí)行類的load方法果漾,再執(zhí)行所有分類的load方法
  • 執(zhí)行類的load方法時(shí),是按照參與編譯的順序執(zhí)行谷誓,先編譯的類先執(zhí)行绒障。
  • 先執(zhí)行父類的load方法,再執(zhí)行自己的load方法
  • 執(zhí)行分類的的load方法時(shí)捍歪,按照分類參與編譯的順序户辱,先參與編譯的分類先執(zhí)行

1.3 執(zhí)行方式

當(dāng)分類中存在和本類中同名的方法時(shí),調(diào)用這個(gè)方法最終執(zhí)行的是分類中的方法糙臼。按理說(shuō)調(diào)用load方法時(shí)最終只會(huì)調(diào)用其中一個(gè)分類的load方法庐镐,可是本類和分類都調(diào)用了load方法

因?yàn)?code>load方法和普通方法調(diào)用方式不同,普通方法調(diào)用時(shí)通過(guò)消息發(fā)送機(jī)制實(shí)現(xiàn)的变逃,會(huì)先去類或元類的方法列表中查找必逆,如果找到了方法就執(zhí)行,如果沒(méi)有找到就去父類的方法列表中查找揽乱,只要找到就會(huì)終止查找末患,所以只會(huì)執(zhí)行一次。

load方法調(diào)用時(shí)锤窑,每個(gè)類都是load方法的地址直接調(diào)用璧针,而不會(huì)走objc_msgSend函數(shù)的方法查找流程,也就是說(shuō)一個(gè)類有時(shí)限load方法就執(zhí)行渊啰,沒(méi)有就不執(zhí)行(沒(méi)有的話也不會(huì)去父類里面查找)

1.4 實(shí)現(xiàn)load方法時(shí)的注意點(diǎn)

我們通常在load方法中進(jìn)行方法交換(Method Swizzle)探橱,除此之外,除非真的有必要绘证,我們盡量不要在load方法中寫(xiě)代碼隧膏,尤其不要在load方法中使用其它的類,因?yàn)檫@個(gè)時(shí)候其它的類可能還沒(méi)有被加載進(jìn)內(nèi)存嚷那,隨意使用可能會(huì)出問(wèn)題胞枕。
如果確實(shí)要在load方法寫(xiě)一些代碼,那也要盡量精簡(jiǎn)代碼魏宽,不要做一些耗時(shí)或者等待鎖的操作腐泻,因?yàn)檎麄€(gè)程序在執(zhí)行load方法時(shí)都會(huì)阻塞决乎,從而導(dǎo)致程序啟動(dòng)時(shí)間過(guò)長(zhǎng)甚至無(wú)法啟動(dòng)。

2. initialize 方法

2.1 調(diào)用時(shí)機(jī)

initialize 方法是在類或者子類收到第一條消息時(shí)被調(diào)用派桩,這里的消息就是指實(shí)例方法或者類方法的調(diào)用构诚,所以所有類的initialize調(diào)用是在main函數(shù)后調(diào)用的。而且一個(gè)類只會(huì)調(diào)用一次initialize 方法铆惑。如果一個(gè)類在城西運(yùn)行過(guò)程中一直沒(méi)有被使用過(guò)范嘱,那這個(gè)類的initialize方法也就不會(huì)被調(diào)用

2.2 調(diào)用方式

initialize方法的調(diào)用和普通方法調(diào)用一樣,也是走的objc_msgSend流程员魏。所以如果一個(gè)類和他的分類都實(shí)現(xiàn)了initialize方法丑蛤,那么最終調(diào)用的是分類中的方法

如果子類和父類都實(shí)現(xiàn)了initialize方法,那么會(huì)先調(diào)用父類的方法撕阎,然后調(diào)用子類的方法盏阶。
子類中不需要寫(xiě)[super initialize]來(lái)調(diào)用父類的方法,通過(guò)查看源碼得知它是在底層實(shí)現(xiàn)過(guò)程中主動(dòng)調(diào)用的父類的initialize方法

2.3 實(shí)現(xiàn)initialize方法時(shí)的注意點(diǎn)

雖然使用initialize要比使用load安全(因?yàn)樵谡{(diào)用initialize時(shí)所有類已經(jīng)被加載進(jìn)內(nèi)存了)闻书,但我們還是要盡量少用initialize這個(gè)方法個(gè)名斟,尤其要謹(jǐn)慎在分類中實(shí)現(xiàn)initialize方法,因?yàn)槿绻诜诸愔袑?shí)現(xiàn)了魄眉,本類實(shí)現(xiàn)的initialize方法將不會(huì)被調(diào)用砰盐。實(shí)際開(kāi)發(fā)中initialize方法一般用于初始化全局變量或靜態(tài)變量。

3 總結(jié)

  • 調(diào)用時(shí)機(jī)和調(diào)用順序不同:

load方法是在類被加載進(jìn)內(nèi)存時(shí)調(diào)用的坑律,在main函數(shù)調(diào)用前被調(diào)用岩梳,且父類,子類晃择,分類都會(huì)被調(diào)用冀值,父類>子類>分類,同一級(jí)別的按編譯順序調(diào)用

initialize方法是在第一次方法調(diào)用時(shí)被調(diào)用宫屠,在main函數(shù)后

  • 執(zhí)行方式不同:

load方法調(diào)用時(shí)列疗,每個(gè)類都是根據(jù)load方法的地址直接調(diào)用,不會(huì)走objc_msgSend流程浪蹂,也就是說(shuō)一個(gè)類有實(shí)現(xiàn)load方法就執(zhí)行抵栈,沒(méi)有就不執(zhí)行,沒(méi)有的話也不會(huì)再父類里面查找

initialize方法調(diào)用方式和objc_msgSend流程一致坤次,initialize默認(rèn)會(huì)調(diào)用[super initialize]

  • 使用模式不同:

load方法常用于方法交換 Method_Swizzle

initialize常用于初始化全局變量或靜態(tài)變量

轉(zhuǎn)載自:https://juejin.im/post/5e130ba05188253a5d560155

?著作權(quán)歸作者所有,轉(zhuǎn)載或內(nèi)容合作請(qǐng)聯(lián)系作者
  • 序言:七十年代末古劲,一起剝皮案震驚了整個(gè)濱河市,隨后出現(xiàn)的幾起案子缰猴,更是在濱河造成了極大的恐慌产艾,老刑警劉巖,帶你破解...
    沈念sama閱讀 222,590評(píng)論 6 517
  • 序言:濱河連續(xù)發(fā)生了三起死亡事件,死亡現(xiàn)場(chǎng)離奇詭異闷堡,居然都是意外死亡隘膘,警方通過(guò)查閱死者的電腦和手機(jī),發(fā)現(xiàn)死者居然都...
    沈念sama閱讀 95,157評(píng)論 3 399
  • 文/潘曉璐 我一進(jìn)店門缚窿,熙熙樓的掌柜王于貴愁眉苦臉地迎上來(lái)棘幸,“玉大人焰扳,你說(shuō)我怎么就攤上這事倦零。” “怎么了吨悍?”我有些...
    開(kāi)封第一講書(shū)人閱讀 169,301評(píng)論 0 362
  • 文/不壞的土叔 我叫張陵扫茅,是天一觀的道長(zhǎng)。 經(jīng)常有香客問(wèn)我育瓜,道長(zhǎng)葫隙,這世上最難降的妖魔是什么? 我笑而不...
    開(kāi)封第一講書(shū)人閱讀 60,078評(píng)論 1 300
  • 正文 為了忘掉前任躏仇,我火速辦了婚禮恋脚,結(jié)果婚禮上,老公的妹妹穿的比我還像新娘焰手。我一直安慰自己糟描,他們只是感情好,可當(dāng)我...
    茶點(diǎn)故事閱讀 69,082評(píng)論 6 398
  • 文/花漫 我一把揭開(kāi)白布书妻。 她就那樣靜靜地躺著船响,像睡著了一般。 火紅的嫁衣襯著肌膚如雪躲履。 梳的紋絲不亂的頭發(fā)上见间,一...
    開(kāi)封第一講書(shū)人閱讀 52,682評(píng)論 1 312
  • 那天,我揣著相機(jī)與錄音工猜,去河邊找鬼米诉。 笑死,一個(gè)胖子當(dāng)著我的面吹牛篷帅,可吹牛的內(nèi)容都是我干的荒辕。 我是一名探鬼主播,決...
    沈念sama閱讀 41,155評(píng)論 3 422
  • 文/蒼蘭香墨 我猛地睜開(kāi)眼犹褒,長(zhǎng)吁一口氣:“原來(lái)是場(chǎng)噩夢(mèng)啊……” “哼抵窒!你這毒婦竟也來(lái)了?” 一聲冷哼從身側(cè)響起叠骑,我...
    開(kāi)封第一講書(shū)人閱讀 40,098評(píng)論 0 277
  • 序言:老撾萬(wàn)榮一對(duì)情侶失蹤李皇,失蹤者是張志新(化名)和其女友劉穎,沒(méi)想到半個(gè)月后,有當(dāng)?shù)厝嗽跇?shù)林里發(fā)現(xiàn)了一具尸體掉房,經(jīng)...
    沈念sama閱讀 46,638評(píng)論 1 319
  • 正文 獨(dú)居荒郊野嶺守林人離奇死亡茧跋,尸身上長(zhǎng)有42處帶血的膿包…… 初始之章·張勛 以下內(nèi)容為張勛視角 年9月15日...
    茶點(diǎn)故事閱讀 38,701評(píng)論 3 342
  • 正文 我和宋清朗相戀三年,在試婚紗的時(shí)候發(fā)現(xiàn)自己被綠了卓囚。 大學(xué)時(shí)的朋友給我發(fā)了我未婚夫和他白月光在一起吃飯的照片瘾杭。...
    茶點(diǎn)故事閱讀 40,852評(píng)論 1 353
  • 序言:一個(gè)原本活蹦亂跳的男人離奇死亡,死狀恐怖哪亿,靈堂內(nèi)的尸體忽然破棺而出粥烁,到底是詐尸還是另有隱情,我是刑警寧澤蝇棉,帶...
    沈念sama閱讀 36,520評(píng)論 5 351
  • 正文 年R本政府宣布讨阻,位于F島的核電站,受9級(jí)特大地震影響篡殷,放射性物質(zhì)發(fā)生泄漏钝吮。R本人自食惡果不足惜,卻給世界環(huán)境...
    茶點(diǎn)故事閱讀 42,181評(píng)論 3 335
  • 文/蒙蒙 一板辽、第九天 我趴在偏房一處隱蔽的房頂上張望奇瘦。 院中可真熱鬧,春花似錦劲弦、人聲如沸耳标。這莊子的主人今日做“春日...
    開(kāi)封第一講書(shū)人閱讀 32,674評(píng)論 0 25
  • 文/蒼蘭香墨 我抬頭看了看天上的太陽(yáng)麻捻。三九已至,卻和暖如春呀袱,著一層夾襖步出監(jiān)牢的瞬間贸毕,已是汗流浹背。 一陣腳步聲響...
    開(kāi)封第一講書(shū)人閱讀 33,788評(píng)論 1 274
  • 我被黑心中介騙來(lái)泰國(guó)打工夜赵, 沒(méi)想到剛下飛機(jī)就差點(diǎn)兒被人妖公主榨干…… 1. 我叫王不留明棍,地道東北人。 一個(gè)月前我還...
    沈念sama閱讀 49,279評(píng)論 3 379
  • 正文 我出身青樓寇僧,卻偏偏與公主長(zhǎng)得像摊腋,于是被迫代替她去往敵國(guó)和親。 傳聞我的和親對(duì)象是個(gè)殘疾皇子嘁傀,可洞房花燭夜當(dāng)晚...
    茶點(diǎn)故事閱讀 45,851評(píng)論 2 361