Runtime objc4-779.1 Runtime在實際開發中的應用之__attribute__

這是一個llvm的指令,很強大,官方文檔中有很多說明,我們這裏記錄我們在開發中可能會遇到的場景和應用

指令格式

__attribute__(相關屬性)

常見場景1 availability 對版本、平臺等情況做說明

在某些時候我們需要對不同的版本和平臺做特別處理,或者API支持,蘋果也有很多這種場景,比如iOS10的系統通知API,UITableView中某些API的限定使用的API_DEPRECATED等宏定義的背後都是用__attribute__(availability...)實現的
eg:
在這裏插入圖片描述

我們如果遇到這種場景大可以使用API_XXXX等宏定義實現我們的需求,但是這裏我們探究一下背後的__attribute__(availability...)

availability的參數如下

  • introduced:引進的版本
  • deprecated:廢棄的版本,還能使用,並沒有移除,而是提醒用戶遷移到其他API
  • obsoleted:移除的版本,不能再使用
  • unavailable:那些平臺不能用
  • message:額外提示信息,比如遷移到某某API

使用ios macosx來指定對應的平臺

實際例子:
在這裏插入圖片描述

效果(實驗環境XCode11.1(11A1027)) iOS 13.1:

在這裏插入圖片描述
系統中的NS_UNAVAILABLE就是使用的第二種方式實現的.

常見場景2 objc_subclassing_restricted 限定被修飾的類不能被其他類繼承

在這裏插入圖片描述
在這裏插入圖片描述

常見場景3 cleanup 修飾一個變量,在它的作用域結束時可以自動執行一個指定的方法

在這裏插入圖片描述
注意:

  • 1,使用cleanup的時候約定調用的方法默認必須需要一個參數,這個參數就是被監聽的對象本身
  • 2,調用方法用C語言,並且形參爲指針的指針
  • 3,可以傳遞block
  • 4,執行順序如下圖所示
    在這裏插入圖片描述

常用場景4 objc_designated_initializer控制初始化方法必須被調用

在系統提供的宏定義中有這麼一個

#define	NS_DESIGNATED_INITIALIZER	__attribute__((objc_designated_initializer))

被它修飾的初始化方法是強制要求被調用的,換句話說就是,如果你在本類中新寫了其他的初始化方法,你也必須在你的方法中調用此方法,所以我們就可以利用這個修飾來寫一個本類必須的初始化過程,然後提供給其他初始化方法使用,或者讓其直接被調用.可以很好的控制本類對象在初始化過程的必要條件保證.

系統中最常見的應用就是NSObject中的init方法
在這裏插入圖片描述
注意事項

事項1: 如果本類有的初始化方法,那麼它必須覆蓋實現父類的objc_designated_initializer方法,否則會有如下警告

在這裏插入圖片描述在這裏插入圖片描述
我們按照警告提示覆寫了父類的init方法,卻出現了另外的警告
在這裏插入圖片描述
大體解釋就是說,因爲你本類有一個objc_designated_initializer初始化方法,那麼,你就必須用本類的初始化方法,而不能用父類的.

在這裏插入圖片描述
果然,將[super init]改成[self init]後不報警告了

對objc_designated_initializer使用總結就是

  • 1, 如果本類有objc_designated_initializer方法,那麼必須重寫父類的objc_designated_initializer方法
  • 2, 初始化方法如果被objc_designated_initializer修飾,那麼在其中必須調用父類的objc_designated_initializer方法
  • 3, 如果本類有objc_designated_initializer初始化方法,那麼其他的非objc_designated_initializer初始化方法必須調用該objc_designated_initializer方法,不能調用父類的.

常見場景5 unused消除對象未被使用警告

在這裏插入圖片描述

常見場景6 objc_requires_super限定方法在重寫時必須先調用父類方法

我們在父類中用objc_requires_super修飾一個方法
在這裏插入圖片描述
在子類中重寫此方法
在這裏插入圖片描述

我們發現就報了讓我們調用父類方法的警告.
在這裏插入圖片描述
遵循提示,我們在重寫時,調用父類方法,警告消失

常用場景6 objc_runtime_name控制類在運行時的名稱

標記TestSon類的運行時名稱爲test_runtime_name
在這裏插入圖片描述
打印
在這裏插入圖片描述
在這裏插入圖片描述
安全加固中的代碼混淆的背後其實就是這個指令,可以防止別人看到我們類真實的名字

總結一下

  • 1, __attribute__的功能很強大,很靈活,在實際開發中我們可以針對不同的應用場景使用不同的指令讓編譯器滿足我們的需求,提高效率,安全
  • 2, __attribute__指令有很多,我們介紹的都是日常會用到的,很多沒有介紹道的,可以查看官方文檔,則需而用.
發表評論
所有評論
還沒有人評論,想成為第一個評論的人麼? 請在上方評論欄輸入並且點擊發布.
相關文章