首页 > IOS

IOS

互联网 2021-04-21 11:59:33

Day28

1.KVO實現原理:

.當某個類的對象第一次被觀察時,系統就會在運行期動態地創建該類的一個派生類,在這個派生類中重寫基類中任何被觀察屬性的setter方法。.派生類在被重寫的setter方法中實現真正的通知機制,就如前面手動實現鍵值觀察那樣。這麼做是基於設置屬性會調用 setter方法,而通過重寫就獲得KVO需要的通知機制。當然前提是要通過遵循KVO的屬性設置方式來變更屬性值,如果僅是直接修改屬性對應的成員變量,是無法實現KVO的。.同時派生類還重寫了class方法以“欺騙”外部調用者它就是起初的那個類。然後系統將這個對象的isa 指針指向這個新誕生的派生類,因此這個對象就成為該派生類的對象了,因而在該對像上對setter的調用就會調用重寫的setter,從而激活鍵值通知機制。此外,派生類還重寫了dealloc方法來釋放資源。

2.change參數默認change參數會包含一個NSKeyValueChangeKindKey鍵值對,傳遞被監聽屬性的變化類型:

typedef NS_ENUM(NSUInteger, NSKeyValueChange) {NSKeyValueChangeSetting = 1,NSKeyValueChangeInsertion = 2,NSKeyValueChangeRemoval = 3,NSKeyValueChangeReplacement = 4,};

NSKeyValueChangeSetting =屬性的值被重新設置;NSKeyValueChangeInsertion、NSKeyValueChangeRemoval、NSKeyValueChangeReplacement =表示更改的是集合屬性,分別代表插入、刪除、替換操作。如果NSKeyValueChangeKindKey參數是針對集合屬性的三個之一,change參數還會包含一個NSKeyValueChangeIndexesKey鍵值對,表示變化的index。(chang字典裡,新值的key為“new”,舊值的key為“old”,變化類型的key為“kind”。)

3、自動通知和手動通知

由於KVO會自動通知觀察者(默認)。固取消自動通知的方法是實現下面的類方法,透過返回NO來取消自動通知。

+ (BOOL) automaticallyNotifiesObserversForKey:(NSString *)key

系統也會單獨針對這個屬性自動生成相關的類方法,是否自動通知這個屬性被改變,也可以單獨重寫這個類方法:

//假如有一個屬性@property (copy, nonatomic) NSString *str;//則系統會自動生成關於這個屬性的類方法,是否自動通知+ (BOOL)automaticallyNotifiesObserversOfTest;

針對非自動通知的屬性,可以分別在變化之前和之後手動調用如下方法(will在前,did在後)來手動通知觀察者:

- (will/did)ChangeValueForKey:- (will/did)ChangeValueForKey:withSetMutation:usingObjects:- (will/did)Change:valuesAtIndexes:forKey:

好處:可以靈活加上自己想要的判斷條件,事實上自動通知也是框架通過調用這些方法實現的。

4.觸發KVO的三種方式:

有訪問器方法,則運行時會在訪問器方法中調用will/didChangeValueForKey:方法;沒有訪問器方法,運行時 會在 setValue:forKey:方法中調用will/didChangeValueForKey:方法。直接使用了訪問器方法(點語法),會在運行時重寫setter方法,調用will/didChangeValueForKey:方法;顯示調用will/didChangeValueForKey:方法。

免责声明:非本网注明原创的信息,皆为程序自动获取互联网,目的在于传递更多信息,并不代表本网赞同其观点和对其真实性负责;如此页面有侵犯到您的权益,请给站长发送邮件,并提供相关证明(版权证明、身份证正反面、侵权链接),站长将在收到邮件12小时内删除。