Objective-C訊息機制的原理

來源:互聯網
上載者:User

  在Objective-C中,message與方法的真正實現是在執行階段綁定的,而非編譯階段。編譯器會將訊息發送轉換成對objc_msgSend方法的調用。
    objc_msgSend方法含兩個必要參數:receiver、方法名(即:selector),如:
    [receiver message]; 將被轉換為:objc_msgSend(receiver, selector);
    objc_msgSend方法也能hold住message的參數,如:
    objc_msgSend(receiver, selector, arg1, arg2, …);

    objc_msgSend方法會做按照順序進行以下操作,以完成動態綁定:
1. 尋找selector所指代的程式(方法的真正實現)。因為不同類對同一方法有不同的實現,所以對方法的真正實現的尋找依賴於receiver的類
2. 調用該實現,並將一系列參數傳遞過去
3. 將該實現的傳回值作為自己的傳回值,返回之

    訊息傳遞的關鍵是,編譯器構建每個類和對象時所採用的資料結構。每個類都包含以下兩個必要元素:
- 一個指向父類的指標。
- 一個調度表(dispatch table)。該調度表將類的selector與方法的實際記憶體位址關聯起來。

    每個對象都有一個指向所屬類的指標isa。通過該指標,對象可以找到它所屬的類,也就找到了其全部父類,如所示:

    當向一個對象發送訊息時,objc_msgSend方法根據對象的isa指標找到對象的類,然後在類的調度表(dispatch table)中尋找selector。如果無法找到selector,objc_msgSend通過指向父類的指標找到父類,並在父類的調度表(dispatch table)中尋找selector,以此類推直到NSObject類。一旦尋找到selector,objc_msgSend方法根據調度表的記憶體位址調用該實現。
    通過這種方式,message與方法的真正實現在執行階段才綁定。

    為了保證訊息發送與執行的效率,系統會將全部selector和使用過的方法的記憶體位址緩衝起來。每個類都有一個獨立的緩衝,緩衝包含有當前類自己的selector以及繼承自父類的selector。尋找調度表(dispatch table)前,訊息發送系統首先檢查receiver對象的緩衝。
    快取命中的情況下,訊息發送(messaging)比直接調用方法(function call)只慢一點點點點。

相關文章

聯繫我們

該頁面正文內容均來源於網絡整理,並不代表阿里雲官方的觀點,該頁面所提到的產品和服務也與阿里云無關,如果該頁面內容對您造成了困擾,歡迎寫郵件給我們,收到郵件我們將在5個工作日內處理。

如果您發現本社區中有涉嫌抄襲的內容,歡迎發送郵件至: info-contact@alibabacloud.com 進行舉報並提供相關證據,工作人員會在 5 個工作天內聯絡您,一經查實,本站將立刻刪除涉嫌侵權內容。

A Free Trial That Lets You Build Big!

Start building with 50+ products and up to 12 months usage for Elastic Compute Service

  • Sales Support

    1 on 1 presale consultation

  • After-Sales Support

    24/7 Technical Support 6 Free Tickets per Quarter Faster Response

  • Alibaba Cloud offers highly flexible support services tailored to meet your exact needs.