OC-終探-對象原理-【Alloc init】

[TOC]

前言

  • 本文主要圍繞以下幾點內容展開討論;

ISA是何時和創建的對象進行綁定的?(ISA最重要的目的就是關聯了對象和類)

ISA的成員(關聯類)

類在內存里面只有一份如何證明?

類、元類、根元類分別是如何指向的?

類的本質是什么?

對象的本質是什么?

ISA成員

isa成員

1、根據nonpointer這個值來判斷當前ISA指向的是純isa指針,還是bits

  • nonpointer為0: 存isa
  • nonpointer為1: 不止是類對象地址,isa包含類信息,對象的引用計數等;

2、has_assoc關聯對象標識符,0沒有,1存在;

3、has_cxx_dtor

has_cxx_dtor

4、shiftcls

shiftcls

5、magicweakly_referenceddeall0catinghas_sidetable_rc

image

6、extra_rc

extra_rc

ISA關聯對象與類

  • ISA綁定代碼
ISA綁定對象
  • ISA64字節成員(x86_64和__arm64是不同的);

二進制打印

p/t打印

八進制打印

p/o打印

十進制打印

p/d打印

對象內存ISA
  • 如何證明ISA指針指向的是當前alloc的類?

方案1

對象內存ISA

方案2
1、x/4gx打印對象的地址值;
2、取出第一位的ISA地址值;
3、獲取當前創建對象的class
4、用當前對象的地址值&ISA_MASK也就是0x00007ffffffffff8
5、最終得到該地址值和第一位的ISA獲取的地址值是一致的,這就驗證了ISA指向的就是當前alloc的類;

  • 代碼走向;
    object_getClass-->obj->getIsa();-->ISA();-->return (Class)(isa.bits & ISA_MASK);

子網掩碼或者位運算的目的都是為了讓某一段內存進行展示

對象內存ISA

類在內存里面只有一份如何證明?

對象內存ISA

思考:子類的ISA和父類的ISA是不是同一個ISA?

答案:肯定不是一個啊!

對象內存ISA

元類&根元類

:代碼寫出來的-->內存只有一份-->不是手動個創建的是系統自己創建的;
元類:系統編譯的-->發現了系統有這樣一個類-->系統也同時創建了編譯器;

對象ISA--> 圖解

對象內存ISA
獲取類的方法
object_getClass(object)

對象ISA-->--類ISA>元類

解釋:對象是由類實例化創建的,那類也是由元類實例化創建的。

對象ISA-->-->元類 圖解

對象內存ISA

對象ISA-->-->元類-->根元類 圖解

對象ISA-->-->元類-->根元類-->根元類 圖解

  • 第一種情況,當創建的對象是NSObject時;
對象內存ISA
  • 第二種情況,當創建的對象是NSObject的子類時;
對象內存ISA
  • 總結:元類和根元類在創建的對象是NSObject時候可能是相同的,但是當創建的對象是NSObject的子類的時候元類和根元類就不是相同的,主要是根據集成的層級管理來決定元類、根元類、根根元類的具體內容;層級越多代表創建的根元類越多;

ISA走位

ISA走位原圖
ISA走位分析圖

要點
1、圖中要分為兩個維度去看(superclass繼承鏈、ISA走位鏈)
2、繼承鏈(子類-->父類-->NSObject類-->nil找方法找不到才指向nil)
3、ISA走位鏈(對象ISA-->-->元類-->根元類-->根元類)
4、根元類也繼承與NSObject

類的本質

xoce快捷鍵:command + shift + 0 進入xcode幫助模式;

官網地址:Type Encodings官網地址

類(NSObject)是什么時候創建的?

答案:NSObject這個基類在程序啟動的時候他就創建了, 在編譯器創建的。

類的本質是什么?

答案:類的本質就是oject_class,是一個結構體!

objc_class內部的結構是什么樣子的?

類的本質

對象的本質

對象的本質是什么?

答案:對象的本質就是結構體!

  • 驗證對象的本質是結構體-步驟1:

1、思考,我們寫的.m文件在xcode編譯的過程中變成了什么?
2、創建一個空的工程, show in finder到.m文件到目錄,打開終端;執行命令; main.m是當前.m文件的名稱,main3.cpp是即將生成文件的名稱;
$ clang -x objective-c -rewrite-objc main.m -o main3.cpp
3、打開main3.cpp文件;


對象的本質

4、找到該對象名對應的結構體截圖;


對象的本質

對象的本質

疑問:默認的成員里面的struct NSObject_IMPL 里面有什么成員?

回答:struct NSObject_IMPL 里面的成員變量是 isa(見下圖)

對象的本質

5、結構體中的NSObject_IVARS成員是繼承來的;其他的成員變量或者屬性是我們聲明出來的;

成員變量和屬性在編譯的過程當中有什么區別?

答案: 成員變量沒有set、get方法,屬性有set、get的方法;

結論: 屬性 = 成員變量 + get方法 + set方法;

對象的本質

備注:如果在使用終端clang命令報錯,報錯內容是"缺少UIKit庫的問題,請執行下面指令到控制臺即可"

對象的本質

總結

ISA是何時和創建的對象進行綁定的?

答案:ISA最重要的目的就是關聯了對象和類 isa <-> cls;

如何獲取一個類的父類?

  • 步驟1

object_getClass方法即可;

Class object_getClass(id obj)
{
    if (obj) return obj->getIsa();
    else return Nil;
}
  • 步驟2

getIsa方法即可;

objc_object::getIsa() 
{
    if (!isTaggedPointer()) return ISA();

    uintptr_t ptr = (uintptr_t)this;
    if (isExtTaggedPointer()) {
        uintptr_t slot = 
            (ptr >> _OBJC_TAG_EXT_SLOT_SHIFT) & _OBJC_TAG_EXT_SLOT_MASK;
        return objc_tag_ext_classes[slot];
    } else {
        uintptr_t slot = 
            (ptr >> _OBJC_TAG_SLOT_SHIFT) & _OBJC_TAG_SLOT_MASK;
        return objc_tag_classes[slot];
    }
}
  • 步驟3

ISA()方法即可;

objc_object::ISA() 
{
    assert(!isTaggedPointer()); 
#if SUPPORT_INDEXED_ISA
    if (isa.nonpointer) {
        uintptr_t slot = isa.indexcls;
        return classForIndex((unsigned)slot);
    }
    return (Class)isa.bits;
#else
    return (Class)(isa.bits & ISA_MASK);
#endif
}
  • 關鍵代碼
    return (Class)(isa.bits & ISA_MASK);

isa.bits就是當前isa指向的地址值,ISA_MASK就是掩碼,這個位置可以看本文ISA關聯對象與類的節點;

ISA指向

對象ISA-->-->元類-->根元類-->根元類

class的繼承管理

子類subclass-->父類superclass-->NSObject-->nil

根元類父類NSObject

類的本質是什么?

結構體;

對象的本質是什么?

結構體;

最后編輯于
?著作權歸作者所有,轉載或內容合作請聯系作者
平臺聲明:文章內容(如有圖片或視頻亦包括在內)由作者上傳并發布,文章內容僅代表作者本人觀點,簡書系信息發布平臺,僅提供信息存儲服務。
  • 序言:七十年代末,一起剝皮案震驚了整個濱河市,隨后出現的幾起案子,更是在濱河造成了極大的恐慌,老刑警劉巖,帶你破解...
    沈念sama閱讀 230,622評論 6 544
  • 序言:濱河連續發生了三起死亡事件,死亡現場離奇詭異,居然都是意外死亡,警方通過查閱死者的電腦和手機,發現死者居然都...
    沈念sama閱讀 99,716評論 3 429
  • 文/潘曉璐 我一進店門,熙熙樓的掌柜王于貴愁眉苦臉地迎上來,“玉大人,你說我怎么就攤上這事。” “怎么了?”我有些...
    開封第一講書人閱讀 178,746評論 0 383
  • 文/不壞的土叔 我叫張陵,是天一觀的道長。 經常有香客問我,道長,這世上最難降的妖魔是什么? 我笑而不...
    開封第一講書人閱讀 63,991評論 1 318
  • 正文 為了忘掉前任,我火速辦了婚禮,結果婚禮上,老公的妹妹穿的比我還像新娘。我一直安慰自己,他們只是感情好,可當我...
    茶點故事閱讀 72,706評論 6 413
  • 文/花漫 我一把揭開白布。 她就那樣靜靜地躺著,像睡著了一般。 火紅的嫁衣襯著肌膚如雪。 梳的紋絲不亂的頭發上,一...
    開封第一講書人閱讀 56,036評論 1 329
  • 那天,我揣著相機與錄音,去河邊找鬼。 笑死,一個胖子當著我的面吹牛,可吹牛的內容都是我干的。 我是一名探鬼主播,決...
    沈念sama閱讀 44,029評論 3 450
  • 文/蒼蘭香墨 我猛地睜開眼,長吁一口氣:“原來是場噩夢啊……” “哼!你這毒婦竟也來了?” 一聲冷哼從身側響起,我...
    開封第一講書人閱讀 43,203評論 0 290
  • 序言:老撾萬榮一對情侶失蹤,失蹤者是張志新(化名)和其女友劉穎,沒想到半個月后,有當地人在樹林里發現了一具尸體,經...
    沈念sama閱讀 49,725評論 1 336
  • 正文 獨居荒郊野嶺守林人離奇死亡,尸身上長有42處帶血的膿包…… 初始之章·張勛 以下內容為張勛視角 年9月15日...
    茶點故事閱讀 41,451評論 3 361
  • 正文 我和宋清朗相戀三年,在試婚紗的時候發現自己被綠了。 大學時的朋友給我發了我未婚夫和他白月光在一起吃飯的照片。...
    茶點故事閱讀 43,677評論 1 374
  • 序言:一個原本活蹦亂跳的男人離奇死亡,死狀恐怖,靈堂內的尸體忽然破棺而出,到底是詐尸還是另有隱情,我是刑警寧澤,帶...
    沈念sama閱讀 39,161評論 5 365
  • 正文 年R本政府宣布,位于F島的核電站,受9級特大地震影響,放射性物質發生泄漏。R本人自食惡果不足惜,卻給世界環境...
    茶點故事閱讀 44,857評論 3 351
  • 文/蒙蒙 一、第九天 我趴在偏房一處隱蔽的房頂上張望。 院中可真熱鬧,春花似錦、人聲如沸。這莊子的主人今日做“春日...
    開封第一講書人閱讀 35,266評論 0 28
  • 文/蒼蘭香墨 我抬頭看了看天上的太陽。三九已至,卻和暖如春,著一層夾襖步出監牢的瞬間,已是汗流浹背。 一陣腳步聲響...
    開封第一講書人閱讀 36,606評論 1 295
  • 我被黑心中介騙來泰國打工, 沒想到剛下飛機就差點兒被人妖公主榨干…… 1. 我叫王不留,地道東北人。 一個月前我還...
    沈念sama閱讀 52,407評論 3 400
  • 正文 我出身青樓,卻偏偏與公主長得像,于是被迫代替她去往敵國和親。 傳聞我的和親對象是個殘疾皇子,可洞房花燭夜當晚...
    茶點故事閱讀 48,643評論 2 380

推薦閱讀更多精彩內容