Runtime和Runloop的區(qū)別

Runtime和Runloop的區(qū)別

一.RunLoop機(jī)制:

Runloop是事件接收和分發(fā)機(jī)制的一個(gè)實(shí)現(xiàn)育叁。

Runloop提供了一種異步執(zhí)行代碼的機(jī)制迅脐,不能并行執(zhí)行任務(wù)。

在主隊(duì)列中豪嗽,Main RunLoop直接配合任務(wù)的執(zhí)行谴蔑,負(fù)責(zé)處理UI事件、定時(shí)器以及其他內(nèi)核相關(guān)事件龟梦。

(1).RunLoop的主要目的:

保證程序執(zhí)行的線程不會(huì)被系統(tǒng)終止隐锭。

(2).什么時(shí)候使用Runloop ?

當(dāng)需要和該線程進(jìn)行交互的時(shí)候才會(huì)使用Runloop.

每一個(gè)線程都有其對(duì)應(yīng)的RunLoop计贰,但是默認(rèn)非主線程的RunLoop是沒有運(yùn)行的钦睡,需要為RunLoop添加至少一個(gè)事件源,然后去run它躁倒。

一般情況下我們是沒有必要去啟用線程的RunLoop的荞怒,除非你在一個(gè)單獨(dú)的線程中需要長(zhǎng)久的檢測(cè)某個(gè)事件洒琢。

主線程??默認(rèn)有Runloop。當(dāng)自己?jiǎn)?dòng)一個(gè)線程褐桌,如果只是用于處理單一的事件衰抑,則該線程在執(zhí)行完之后就退出了。所以當(dāng)我們需要讓該線程監(jiān)聽某項(xiàng)事務(wù)

時(shí)荧嵌,就得讓線程一直不退出停士,runloop就是這么一個(gè)循環(huán),沒有事件的時(shí)候完丽,一直卡著,有事件來臨了拇舀,執(zhí)行其對(duì)應(yīng)的函數(shù)逻族。

RunLoop,正如其名所示,是線程進(jìn)入和被線程用來相應(yīng)事件以及調(diào)用事件處理函數(shù)的地方.需要在代碼中使用控制語句實(shí)現(xiàn)RunLoop的循環(huán),也就是說,需要代碼提供while或者for循環(huán)來驅(qū)動(dòng)RunLoop.

在這個(gè)循環(huán)中,使用一個(gè)runLoop對(duì)象[NSRunloop currentRunloop]執(zhí)行接收消息,調(diào)用對(duì)應(yīng)的處理函數(shù).

Runloop接收兩種源事件:input sources和timer sources。

input sources?傳遞異步事件骄崩,通常是來自其他線程和不同的程序中的消息聘鳞;

timer sources(定時(shí)器)?傳遞同步事件(重復(fù)執(zhí)行或者在特定時(shí)間上觸發(fā))。

除了處理input sources要拂,Runloop

也會(huì)產(chǎn)生一些關(guān)于本身行為的notificaiton抠璃。注冊(cè)成為Runloop的observer,可以接收到這些notification脱惰,做一些額外

的處理搏嗡。(使用CoreFoundation來成為runloop的observer)。

Runloop工作的特點(diǎn):

1>當(dāng)有時(shí)間發(fā)生時(shí),Runloop會(huì)根據(jù)具體的事件類型通知應(yīng)用程序作出相應(yīng);

2>當(dāng)沒有事件發(fā)生時(shí),Runloop會(huì)進(jìn)入休眠狀態(tài),從而達(dá)到省電的目的;

3>當(dāng)事件再次發(fā)生時(shí),Runloop會(huì)被重新喚醒,處理事件.

提示:一般在開發(fā)中很少會(huì)主動(dòng)創(chuàng)建Runloop,而通常會(huì)把事件添加到Runloop中.

二.Runtime機(jī)制:

RunTime簡(jiǎn)稱運(yùn)行時(shí)拉一。就是系統(tǒng)在運(yùn)行的時(shí)候的一些機(jī)制采盒,其中最主要的是消息機(jī)制。對(duì)于C語言蔚润,函數(shù)的調(diào)用在編譯的時(shí)候會(huì)決定調(diào)用哪個(gè)函數(shù)(

C語言的函數(shù)調(diào)用請(qǐng)看這里

)磅氨。編譯完成之后直接順序執(zhí)行,無任何二義性嫡纠。OC的函數(shù)調(diào)用成為消息發(fā)送烦租。屬于動(dòng)態(tài)調(diào)用過程。在編譯的時(shí)候并不能決定真正調(diào)用哪個(gè)函數(shù)(事實(shí)證明除盏,在編

譯階段叉橱,OC可以調(diào)用任何函數(shù),即使這個(gè)函數(shù)并未實(shí)現(xiàn)痴颊,只要申明過就不會(huì)報(bào)錯(cuò)赏迟。而C語言在編譯階段就會(huì)報(bào)錯(cuò))。只有在真正運(yùn)行的時(shí)候才會(huì)根據(jù)函數(shù)的名稱找

到對(duì)應(yīng)的函數(shù)來調(diào)用蠢棱。

那OC是怎么實(shí)現(xiàn)動(dòng)態(tài)調(diào)用的呢锌杀?下面我們來看看OC通過發(fā)送消息來達(dá)到動(dòng)態(tài)調(diào)用的秘密甩栈。假如在OC中寫了這樣的一個(gè)代碼:

[objc] view plain?

[obj?makeText];

其中obj是一個(gè)對(duì)象,makeText是一個(gè)函數(shù)名稱糕再。對(duì)于這樣一個(gè)簡(jiǎn)單的調(diào)用量没。在編譯時(shí)RunTime會(huì)將上述代碼轉(zhuǎn)化成

[objc] view plain?

objc_msgSend(obj,@selector(makeText));

首先我們來看看obj這個(gè)對(duì)象,iOS中的obj都繼承于NSObject突想。

[objc] view plain?

@interface?NSObject??{

Class?isa??OBJC_ISA_AVAILABILITY;

}

在NSObjcet中存在一個(gè)Class的isa指針殴蹄。然后我們看看Class:

[objc] view plain?

typedef?struct?objc_class?*Class;

struct?objc_class?{

Class?isa;?//?指向metaclass

Class?super_class?;?//?指向其父類

const?charchar?*name?;?//?類名

long?version?;?//?類的版本信息,初始化默認(rèn)為0猾担,可以通過runtime函數(shù)class_setVersion和class_getVersion進(jìn)行修改袭灯、讀取

long?info;?//?一些標(biāo)識(shí)信息,如CLS_CLASS?(0x1L)?表示該類為普通?class?,其中包含對(duì)象方法和成員變量;CLS_META?(0x2L)?表示該類為?metaclass绑嘹,其中包含類方法;

long?instance_size?;?//?該類的實(shí)例變量大小(包括從父類繼承下來的實(shí)例變量);

struct?objc_ivar_list?*ivars;?//?用于存儲(chǔ)每個(gè)成員變量的地址

struct?objc_method_list?**methodLists?;?//?與?info?的一些標(biāo)志位有關(guān),如CLS_CLASS?(0x1L),則存儲(chǔ)對(duì)象方法稽荧,如CLS_META?(0x2L),則存儲(chǔ)類方法;

struct?objc_cache?*cache;?//?指向最近使用的方法的指針工腋,用于提升效率姨丈;

struct?objc_protocol_list?*protocols;?//?存儲(chǔ)該類遵守的協(xié)議

}

我們可以看到,對(duì)于一個(gè)Class類中擅腰,存在很多東西蟋恬,下面我來一一解釋一下:

Class

isa:指向metaclass,也就是靜態(tài)的Class趁冈。一般一個(gè)Obj對(duì)象中的isa會(huì)指向普通的Class歼争,這個(gè)Class中存儲(chǔ)普通成員變量和對(duì)

象方法(“-”開頭的方法),普通Class中的isa指針指向靜態(tài)Class箱歧,靜態(tài)Class中存儲(chǔ)static類型成員變量和類方法(“+”開頭的方

法)矾飞。

Class super_class:指向父類,如果這個(gè)類是根類呀邢,則為NULL洒沦。

注意:所有metaclass中isa指針都指向跟metaclass。而跟metaclass則指向自身价淌。

Root metaclass是通過繼承Root class產(chǎn)生的申眼。與root class結(jié)構(gòu)體成員一致,也就是前面提到的結(jié)構(gòu)蝉衣。不同的是Root

metaclass的isa指針指向自身括尸。

Class類中其他的成員這里就先不做過多解釋了,下面我們來看看:

@selector (makeText):

這是一個(gè)SEL方法選擇器病毡。SEL其主要作用是快速的通過方法名字(makeText)查找到對(duì)應(yīng)方法的函數(shù)指針濒翻,然后調(diào)用其函數(shù)。SEL其本身是一個(gè)

Int類型的一個(gè)地址,地址中存放著方法的名字有送。對(duì)于一個(gè)類中淌喻。每一個(gè)方法對(duì)應(yīng)著一個(gè)SEL。所以iOS類中不能存在2個(gè)名稱相同的方法雀摘,即使參數(shù)類型不

同裸删,因?yàn)镾EL是根據(jù)方法名字生成的,相同的方法名稱只能對(duì)應(yīng)一個(gè)SEL阵赠。

下面我們就來看看具體消息發(fā)送之后是怎么來動(dòng)態(tài)查找對(duì)應(yīng)的方法的涯塔。

首先,編譯器將代碼[obj makeText];轉(zhuǎn)化為objc_msgSend(obj, @selector

(makeText));清蚀,在objc_msgSend函數(shù)中匕荸。首先通過obj的isa指針找到obj對(duì)應(yīng)的class。在Class中先去cache中

通過SEL查找對(duì)應(yīng)函數(shù)method(猜測(cè)cache中method列表是以SEL為key通過hash表來存儲(chǔ)的枷邪,這樣能提高函數(shù)查找速度)每聪,若

cache中未找到。再去methodList中查找齿风,若methodlist中未找到,則取superClass中查找绑洛。若能找到救斑,則將method加

入到cache中,以方便下次查找真屯,并通過method中的函數(shù)指針跳轉(zhuǎn)到對(duì)應(yīng)的函數(shù)中去執(zhí)行脸候。

?著作權(quán)歸作者所有,轉(zhuǎn)載或內(nèi)容合作請(qǐng)聯(lián)系作者
  • 序言:七十年代末,一起剝皮案震驚了整個(gè)濱河市绑蔫,隨后出現(xiàn)的幾起案子运沦,更是在濱河造成了極大的恐慌,老刑警劉巖配深,帶你破解...
    沈念sama閱讀 216,402評(píng)論 6 499
  • 序言:濱河連續(xù)發(fā)生了三起死亡事件携添,死亡現(xiàn)場(chǎng)離奇詭異,居然都是意外死亡篓叶,警方通過查閱死者的電腦和手機(jī)烈掠,發(fā)現(xiàn)死者居然都...
    沈念sama閱讀 92,377評(píng)論 3 392
  • 文/潘曉璐 我一進(jìn)店門,熙熙樓的掌柜王于貴愁眉苦臉地迎上來缸托,“玉大人左敌,你說我怎么就攤上這事±洌” “怎么了矫限?”我有些...
    開封第一講書人閱讀 162,483評(píng)論 0 353
  • 文/不壞的土叔 我叫張陵,是天一觀的道長(zhǎng)。 經(jīng)常有香客問我叼风,道長(zhǎng)取董,這世上最難降的妖魔是什么? 我笑而不...
    開封第一講書人閱讀 58,165評(píng)論 1 292
  • 正文 為了忘掉前任咬扇,我火速辦了婚禮甲葬,結(jié)果婚禮上,老公的妹妹穿的比我還像新娘懈贺。我一直安慰自己经窖,他們只是感情好,可當(dāng)我...
    茶點(diǎn)故事閱讀 67,176評(píng)論 6 388
  • 文/花漫 我一把揭開白布梭灿。 她就那樣靜靜地躺著画侣,像睡著了一般。 火紅的嫁衣襯著肌膚如雪堡妒。 梳的紋絲不亂的頭發(fā)上配乱,一...
    開封第一講書人閱讀 51,146評(píng)論 1 297
  • 那天,我揣著相機(jī)與錄音皮迟,去河邊找鬼搬泥。 笑死,一個(gè)胖子當(dāng)著我的面吹牛伏尼,可吹牛的內(nèi)容都是我干的忿檩。 我是一名探鬼主播,決...
    沈念sama閱讀 40,032評(píng)論 3 417
  • 文/蒼蘭香墨 我猛地睜開眼爆阶,長(zhǎng)吁一口氣:“原來是場(chǎng)噩夢(mèng)啊……” “哼燥透!你這毒婦竟也來了?” 一聲冷哼從身側(cè)響起辨图,我...
    開封第一講書人閱讀 38,896評(píng)論 0 274
  • 序言:老撾萬榮一對(duì)情侶失蹤班套,失蹤者是張志新(化名)和其女友劉穎,沒想到半個(gè)月后故河,有當(dāng)?shù)厝嗽跇淞掷锇l(fā)現(xiàn)了一具尸體吱韭,經(jīng)...
    沈念sama閱讀 45,311評(píng)論 1 310
  • 正文 獨(dú)居荒郊野嶺守林人離奇死亡,尸身上長(zhǎng)有42處帶血的膿包…… 初始之章·張勛 以下內(nèi)容為張勛視角 年9月15日...
    茶點(diǎn)故事閱讀 37,536評(píng)論 2 332
  • 正文 我和宋清朗相戀三年鱼的,在試婚紗的時(shí)候發(fā)現(xiàn)自己被綠了杉女。 大學(xué)時(shí)的朋友給我發(fā)了我未婚夫和他白月光在一起吃飯的照片。...
    茶點(diǎn)故事閱讀 39,696評(píng)論 1 348
  • 序言:一個(gè)原本活蹦亂跳的男人離奇死亡鸳吸,死狀恐怖熏挎,靈堂內(nèi)的尸體忽然破棺而出,到底是詐尸還是另有隱情晌砾,我是刑警寧澤坎拐,帶...
    沈念sama閱讀 35,413評(píng)論 5 343
  • 正文 年R本政府宣布,位于F島的核電站,受9級(jí)特大地震影響哼勇,放射性物質(zhì)發(fā)生泄漏都伪。R本人自食惡果不足惜,卻給世界環(huán)境...
    茶點(diǎn)故事閱讀 41,008評(píng)論 3 325
  • 文/蒙蒙 一积担、第九天 我趴在偏房一處隱蔽的房頂上張望陨晶。 院中可真熱鬧,春花似錦帝璧、人聲如沸先誉。這莊子的主人今日做“春日...
    開封第一講書人閱讀 31,659評(píng)論 0 22
  • 文/蒼蘭香墨 我抬頭看了看天上的太陽褐耳。三九已至,卻和暖如春渴庆,著一層夾襖步出監(jiān)牢的瞬間铃芦,已是汗流浹背。 一陣腳步聲響...
    開封第一講書人閱讀 32,815評(píng)論 1 269
  • 我被黑心中介騙來泰國(guó)打工襟雷, 沒想到剛下飛機(jī)就差點(diǎn)兒被人妖公主榨干…… 1. 我叫王不留刃滓,地道東北人。 一個(gè)月前我還...
    沈念sama閱讀 47,698評(píng)論 2 368
  • 正文 我出身青樓耸弄,卻偏偏與公主長(zhǎng)得像注盈,于是被迫代替她去往敵國(guó)和親。 傳聞我的和親對(duì)象是個(gè)殘疾皇子叙赚,可洞房花燭夜當(dāng)晚...
    茶點(diǎn)故事閱讀 44,592評(píng)論 2 353

推薦閱讀更多精彩內(nèi)容

  • Runloop 做了一年多的IOS開發(fā),對(duì)IOS和Objective-C深層次的了解還十分有限僚饭,大多還停留在會(huì)用A...
    GitHubPorter閱讀 6,058評(píng)論 7 17
  • runtime 和 runloop 作為一個(gè)程序員進(jìn)階是必須的震叮,也是非常重要的, 在面試過程中是經(jīng)常會(huì)被問到的鳍鸵, ...
    made_China閱讀 1,210評(píng)論 0 7
  • 轉(zhuǎn)至元數(shù)據(jù)結(jié)尾創(chuàng)建: 董瀟偉苇瓣,最新修改于: 十二月 23, 2016 轉(zhuǎn)至元數(shù)據(jù)起始第一章:isa和Class一....
    40c0490e5268閱讀 1,709評(píng)論 0 9
  • runtime 和 runloop 作為一個(gè)程序員進(jìn)階是必須的,也是非常重要的偿乖, 在面試過程中是經(jīng)常會(huì)被問到的击罪, ...
    SOI閱讀 21,802評(píng)論 3 63
  • 我們常常會(huì)聽說 Objective-C 是一門動(dòng)態(tài)語言,那么這個(gè)「動(dòng)態(tài)」表現(xiàn)在哪呢贪薪?我想最主要的表現(xiàn)就是 Obje...
    Ethan_Struggle閱讀 2,192評(píng)論 0 7