Swift內(nèi)存管理

內(nèi)存分配

堆是完全二叉樹料仗,底層節(jié)點填充是按照從左到右的順序進(jìn)行,Swift的堆是通過雙向鏈表實現(xiàn)的意敛,由于堆可以reatin和release馅巷,所以很容易使內(nèi)存不連續(xù),采用鏈表的形式是為了將內(nèi)存連起來草姻,release通過鏈表來整合空間

Weak

Swift4.0以前是對象強引用技術(shù)為0后钓猬,看弱引用技術(shù)來決定是否保留釋放對象所占用內(nèi)存,如果引用計數(shù)不為0撩独,那么內(nèi)存還會保留原來的內(nèi)存敞曹,知道引用計數(shù)為0才會被清理掉,综膀,為了避免這總情況澳迫,新版Swift引入了SideTable,讓對象弱引用指針指向?qū)?yīng)的sidetable剧劝,這樣做的好處是僵尸對象長期占用內(nèi)存的情況橄登,不需要保留僵尸對象,只保留引用計數(shù)和指向源對象指針內(nèi)存占用空間小

棧的結(jié)構(gòu)比較簡單只有push和pop,內(nèi)存上只需要維護(hù)棧末端指針即可示绊,

派發(fā)機制

Swift派發(fā)目的是為了讓cpu知道被調(diào)用函數(shù)在哪里锭部,Swift支持 直接派發(fā)、函數(shù)表派發(fā)面褐、消息機制派發(fā)這三種機制拌禾。

直接派發(fā)

C++使用的是直接派發(fā),這樣做的優(yōu)勢是調(diào)用指令少展哭,缺點是缺少動態(tài)性

函數(shù)表派發(fā)

Java使用的派發(fā)方式是函數(shù)表派發(fā)湃窍,通過Final修飾的方法為直接派發(fā),而函數(shù)表派發(fā)具有動態(tài)性匪傍,一個類會用數(shù)組來存儲函數(shù)指針您市,重寫父類函數(shù)會替代以前的函數(shù)
舉個例子

class Fish {
    func swim() {}
    func eat() {}
}

class FlyingFish: Finsh {
    override func eat() {}
   func fly() {}
}

編譯器會給Fish和FlyingFish分別創(chuàng)建函數(shù)表,在Fish函數(shù)里有swim和eat函數(shù)沒再FlyingFish函數(shù)里有父類Fish的Swim和覆蓋了父類eat方法的函數(shù)以及新的fly函數(shù)

函數(shù)被調(diào)用有點讀取對象的函數(shù)表役衡,再根據(jù)該函數(shù)的偏移量的導(dǎo)函數(shù)地址在跳轉(zhuǎn)到相應(yīng)地址去茵休,比直接派發(fā)慢

消息機制派發(fā)

消息機制派發(fā)是在運行時可以改變函數(shù)的行為,kvo是對這種機制的運用手蝎,oc使用的是動態(tài)派發(fā)機制榕莺,c用的是直接派發(fā),所以c的性能高棵介,Swift可以通過dynamic方式使其支持動態(tài)派發(fā)钉鸯,當(dāng)一個消息被派發(fā)程序就需要按照集成關(guān)系向上查找被調(diào)用的函數(shù),但是這樣做效率不高邮辽,所以通過緩存來提高效率唠雕,這樣查找性能就和函數(shù)派發(fā)差不多了

派發(fā)使用場景

值類型使用的是直接派發(fā)
類和協(xié)議的extension是直接派發(fā)
類和協(xié)議的初始化使用的是函數(shù)表派發(fā)
@objc extension 使用的是消息機制派發(fā)

派發(fā)方式如下所示

final: 讓類里的函數(shù)使用直接派發(fā),這樣該函數(shù)沒有動態(tài)性程序運行也無法讀取到這個函數(shù)
dynamic: 讓類里的函數(shù)使用消息機制轉(zhuǎn)發(fā)可以重載extension函數(shù)吨述,
Swift會在派發(fā)上做優(yōu)化岩睁,如果函數(shù)沒有重載那么會用直接派發(fā)方式,如果屬性綁定kvo锐极,那么他的get set 方法可能會被優(yōu)化成直接派發(fā)笙僚,從而導(dǎo)致kvo失效,所以需要加上dynamic來保證kvo有效灵再。

基本數(shù)據(jù)內(nèi)存管理/結(jié)構(gòu)體內(nèi)存管理

結(jié)構(gòu)體和基本數(shù)據(jù)類型編譯時就可以確定內(nèi)存大小肋层,所以程序運行時不需要額外內(nèi)存空間因此函數(shù)調(diào)用就是直接傳地址

內(nèi)存對齊
操作系統(tǒng)在編譯的過程中,會以結(jié)構(gòu)體中成員的最大值作為其對齊的值翎迁,這是因為操作系統(tǒng)在數(shù)據(jù)讀取的時候栋猖,其實并不是一個字節(jié)一個字節(jié)進(jìn)行讀取的,而是一段一段進(jìn)行讀取汪榔,我們假如是4bytes蒲拉。假如我們要讀取一個int,這個int是從第1位到第4位。那么讀取的時候會發(fā)生什么事情呢雌团?首先我們需要先讀第一塊數(shù)據(jù)燃领,然后讀取后三位的數(shù)據(jù)。接下來锦援,讀取第二塊數(shù)據(jù)猛蔽,然后只取第一位的數(shù)據(jù)。最后將兩次的數(shù)據(jù)組合起來灵寺,就是我們想要的一個數(shù)據(jù)曼库。對于操作系統(tǒng)來說,這種處理數(shù)據(jù)的方式并不是特別地高效略板。我們都知道毁枯,在計算機領(lǐng)域,有一個特別有名的優(yōu)化手段叮称,就是空間換時間种玛。我們通過內(nèi)存對齊,直接跳過部分空的字節(jié)颅拦,然后一次性讀取所需數(shù)據(jù)蒂誉。內(nèi)存對齊的規(guī)則如下教藻,基本類型的對齊值距帅,其實就是他們的sizeof值。而結(jié)構(gòu)體的對齊值括堤,就是結(jié)構(gòu)體中最大的對齊值碌秸。

那么,知道內(nèi)存對齊了之后悄窃,有什么作用呢讥电?假如我們的一個結(jié)構(gòu)體有1個int,兩個char, 那么不同的排列順序轧抗,會造成結(jié)構(gòu)體的大小不一致恩敌。


我們注意到,不同的排列順序最終會讓結(jié)構(gòu)體占用不同的內(nèi)存横媚。雖然這些只是非常小的細(xì)節(jié)纠炮,但是在開發(fā)過程中,假如我們能夠注意到這些細(xì)節(jié)灯蝴,必將事半功倍恢口。

class 內(nèi)存管理

類本身實在對堆上進(jìn)行分配的,在Heap上還需要保存class的Type信息穷躁,Type信息有個函數(shù)表耕肩,類的函數(shù)在派發(fā)的時候會按照函數(shù)表派發(fā),子類需要繼承父類時只要在type里記錄自己信息即可

協(xié)議/泛型 內(nèi)存管理

存儲在一個existential container容器中,該容器的大致結(jié)構(gòu)是{ heapObject, metadata, PWT }

?著作權(quán)歸作者所有,轉(zhuǎn)載或內(nèi)容合作請聯(lián)系作者
  • 序言:七十年代末猿诸,一起剝皮案震驚了整個濱河市婚被,隨后出現(xiàn)的幾起案子,更是在濱河造成了極大的恐慌梳虽,老刑警劉巖摔寨,帶你破解...
    沈念sama閱讀 216,544評論 6 501
  • 序言:濱河連續(xù)發(fā)生了三起死亡事件,死亡現(xiàn)場離奇詭異怖辆,居然都是意外死亡是复,警方通過查閱死者的電腦和手機,發(fā)現(xiàn)死者居然都...
    沈念sama閱讀 92,430評論 3 392
  • 文/潘曉璐 我一進(jìn)店門竖螃,熙熙樓的掌柜王于貴愁眉苦臉地迎上來淑廊,“玉大人,你說我怎么就攤上這事特咆〖境停” “怎么了?”我有些...
    開封第一講書人閱讀 162,764評論 0 353
  • 文/不壞的土叔 我叫張陵腻格,是天一觀的道長画拾。 經(jīng)常有香客問我,道長菜职,這世上最難降的妖魔是什么青抛? 我笑而不...
    開封第一講書人閱讀 58,193評論 1 292
  • 正文 為了忘掉前任,我火速辦了婚禮酬核,結(jié)果婚禮上蜜另,老公的妹妹穿的比我還像新娘。我一直安慰自己嫡意,他們只是感情好举瑰,可當(dāng)我...
    茶點故事閱讀 67,216評論 6 388
  • 文/花漫 我一把揭開白布。 她就那樣靜靜地躺著蔬螟,像睡著了一般此迅。 火紅的嫁衣襯著肌膚如雪。 梳的紋絲不亂的頭發(fā)上旧巾,一...
    開封第一講書人閱讀 51,182評論 1 299
  • 那天耸序,我揣著相機與錄音,去河邊找鬼菠齿。 笑死佑吝,一個胖子當(dāng)著我的面吹牛,可吹牛的內(nèi)容都是我干的绳匀。 我是一名探鬼主播芋忿,決...
    沈念sama閱讀 40,063評論 3 418
  • 文/蒼蘭香墨 我猛地睜開眼炸客,長吁一口氣:“原來是場噩夢啊……” “哼!你這毒婦竟也來了戈钢?” 一聲冷哼從身側(cè)響起痹仙,我...
    開封第一講書人閱讀 38,917評論 0 274
  • 序言:老撾萬榮一對情侶失蹤,失蹤者是張志新(化名)和其女友劉穎殉了,沒想到半個月后开仰,有當(dāng)?shù)厝嗽跇淞掷锇l(fā)現(xiàn)了一具尸體,經(jīng)...
    沈念sama閱讀 45,329評論 1 310
  • 正文 獨居荒郊野嶺守林人離奇死亡薪铜,尸身上長有42處帶血的膿包…… 初始之章·張勛 以下內(nèi)容為張勛視角 年9月15日...
    茶點故事閱讀 37,543評論 2 332
  • 正文 我和宋清朗相戀三年众弓,在試婚紗的時候發(fā)現(xiàn)自己被綠了。 大學(xué)時的朋友給我發(fā)了我未婚夫和他白月光在一起吃飯的照片隔箍。...
    茶點故事閱讀 39,722評論 1 348
  • 序言:一個原本活蹦亂跳的男人離奇死亡谓娃,死狀恐怖,靈堂內(nèi)的尸體忽然破棺而出蜒滩,到底是詐尸還是另有隱情滨达,我是刑警寧澤,帶...
    沈念sama閱讀 35,425評論 5 343
  • 正文 年R本政府宣布俯艰,位于F島的核電站捡遍,受9級特大地震影響,放射性物質(zhì)發(fā)生泄漏竹握。R本人自食惡果不足惜画株,卻給世界環(huán)境...
    茶點故事閱讀 41,019評論 3 326
  • 文/蒙蒙 一、第九天 我趴在偏房一處隱蔽的房頂上張望涩搓。 院中可真熱鬧污秆,春花似錦、人聲如沸昧甘。這莊子的主人今日做“春日...
    開封第一講書人閱讀 31,671評論 0 22
  • 文/蒼蘭香墨 我抬頭看了看天上的太陽充边。三九已至,卻和暖如春常侦,著一層夾襖步出監(jiān)牢的瞬間浇冰,已是汗流浹背。 一陣腳步聲響...
    開封第一講書人閱讀 32,825評論 1 269
  • 我被黑心中介騙來泰國打工聋亡, 沒想到剛下飛機就差點兒被人妖公主榨干…… 1. 我叫王不留肘习,地道東北人。 一個月前我還...
    沈念sama閱讀 47,729評論 2 368
  • 正文 我出身青樓坡倔,卻偏偏與公主長得像漂佩,于是被迫代替她去往敵國和親脖含。 傳聞我的和親對象是個殘疾皇子,可洞房花燭夜當(dāng)晚...
    茶點故事閱讀 44,614評論 2 353

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