NSKeyValueObservingOptions詳解

options是KVO中常見的參數(shù)捎迫,然而通常只是將它固定為“NSKeyValueObservingOptionNew | NSKeyValueObservingOptionOld”來使用卻不知道到底這個參數(shù)有什么用统刮。由此本文通過一個例子來描述該參數(shù)的實際表現(xiàn)。


NSKeyValueObservingOptions是options的類型(

- (void)addObserver:(NSObject *)observer

? ? ? ? ? ? ?forKeyPath:(NSString *)keyPath

? ? ? ? ? ? ? ? ?options:(NSKeyValueObservingOptions)options

? ? ? ? ? ? ? ? ? context:(void *)context


首先看頭文件中的定義:

typedefNS_OPTIONS(NSUInteger, NSKeyValueObservingOptions) {

/* Whether the change dictionaries sent in notifications should contain NSKeyValueChangeNewKey and NSKeyValueChangeOldKey entries, respectively.

*/

NSKeyValueObservingOptionNew =0x01,

NSKeyValueObservingOptionOld =0x02,

/* Whether a notification should be sent to the observer immediately, before the observer registration method even returns. The change dictionary in the notification will always contain an NSKeyValueChangeNewKey entry if NSKeyValueObservingOptionNew is also specified but will never contain an NSKeyValueChangeOldKey entry. (In an initial notification the current value of the observed property may be old, but it's new to the observer.) You can use this option instead of explicitly invoking, at the same time, code that is also invoked by the observer's -observeValueForKeyPath:ofObject:change:context: method. When this option is used with -addObserver:toObjectsAtIndexes:forKeyPath:options:context: a notification will be sent for each indexed object to which the observer is being added.

*/

NSKeyValueObservingOptionInitial NS_ENUM_AVAILABLE(10_5,2_0) =0x04,

/* Whether separate notifications should be sent to the observer before and after each change, instead of a single notification after the change. The change dictionary in a notification sent before a change always contains an NSKeyValueChangeNotificationIsPriorKey entry whose value is [NSNumber numberWithBool:YES], but never contains an NSKeyValueChangeNewKey entry. You can use this option when the observer's own KVO-compliance requires it to invoke one of the -willChange... methods for one of its own properties, and the value of that property depends on the value of the observed object's property. (In that situation it's too late to easily invoke -willChange... properly in response to receiving an -observeValueForKeyPath:ofObject:change:context: message after the change.)

When this option is specified, the change dictionary in a notification sent after a change contains the same entries that it would contain if this option were not specified, except for ordered unique to-many relationships represented by NSOrderedSets.For those, for NSKeyValueChangeInsertion and NSKeyValueChangeReplacement changes, the change dictionary for a will-change notification contains an NSKeyValueChangeIndexesKey (and NSKeyValueChangeOldKey in the case of Replacement where the NSKeyValueObservingOptionOld option was specified at registration time) which give the indexes (and objects) which *may* be changed by the operation.The second notification, after the change, contains entries reporting what did actually change.For NSKeyValueChangeRemoval changes, removals by index are precise.

*/

NSKeyValueObservingOptionPrior NS_ENUM_AVAILABLE(10_5,2_0) =0x08

};

可以很清楚的看到污抬,其中包含了四種值汞贸,分別為:

NSKeyValueObservingOptionNew:提供更改前的值

NSKeyValueObservingOptionOld:提供更改后的值

NSKeyValueObservingOptionInitial:觀察最初的值(在注冊觀察服務(wù)時會調(diào)用一次觸發(fā)方法)

NSKeyValueObservingOptionPrior:分別在值修改前后觸發(fā)方法(即一次修改有兩次觸發(fā))


以下是一個簡單的測試案例:


測試代碼

將options修改為NSKeyValueObservingOptionNew得到測試結(jié)果:

2016-07-04 19:18:29.265 testForKVO[50887:35316085] turn1

2016-07-04 19:18:29.265 testForKVO[50887:35316085] ? ?kind: 1

2016-07-04 19:18:29.266 testForKVO[50887:35316085] ? ?new: turn1

2016-07-04 19:18:29.266 testForKVO[50887:35316085] turn2

2016-07-04 19:18:29.266 testForKVO[50887:35316085] ? ?kind: 1

2016-07-04 19:18:29.266 testForKVO[50887:35316085] ? ?new: turn2

可以看到觀察被觸發(fā)2次,在change對象中包含key為new的值印机,并且為stringA的最新值


將options修改為NSKeyValueObservingOptionOld得到測試結(jié)果:

2016-07-04 19:19:14.562 testForKVO[50912:35317211] turn1

2016-07-04 19:19:14.562 testForKVO[50912:35317211] ? ?kind: 1

2016-07-04 19:19:14.562 testForKVO[50912:35317211] ? ?old: turn0

2016-07-04 19:19:14.563 testForKVO[50912:35317211] turn2

2016-07-04 19:19:14.563 testForKVO[50912:35317211] ? ?kind: 1

2016-07-04 19:19:14.563 testForKVO[50912:35317211] ? ?old: turn1

可以看到觀察被觸發(fā)2次矢腻,在change對象中包含key為old的值,并且為stringA被修改前的值


將options修改為NSKeyValueObservingOptionInitial得到測試結(jié)果:

//注冊觀察服務(wù)時

2016-07-04 19:20:08.003 testForKVO[50938:35318482] turn0

2016-07-04 19:20:08.004 testForKVO[50938:35318482] ? ?kind: 1

//self.stringA=@"turn1";

2016-07-04 19:20:08.004 testForKVO[50938:35318482] turn1

2016-07-04 19:20:08.004 testForKVO[50938:35318482] ? ?kind: 1

//self.stringA=@"turn2";

2016-07-04 19:20:08.004 testForKVO[50938:35318482] turn2

2016-07-04 19:20:08.005 testForKVO[50938:35318482] ? ?kind: 1

可以看到觀察被觸發(fā)3次耳贬,在觀察服務(wù)注冊時踏堡,執(zhí)行了一次觸發(fā)


將options修改為NSKeyValueObservingOptionPrior得到測試結(jié)果:

2016-07-04 19:20:47.936 testForKVO[50962:35319521] turn0

2016-07-04 19:20:47.937 testForKVO[50962:35319521] ? ?kind: 1

2016-07-04 19:20:47.937 testForKVO[50962:35319521] ? ?notificationIsPrior: 1

2016-07-04 19:20:47.937 testForKVO[50962:35319521] turn1

2016-07-04 19:20:47.937 testForKVO[50962:35319521] ? ?kind: 1

2016-07-04 19:20:47.937 testForKVO[50962:35319521] turn1

2016-07-04 19:20:47.938 testForKVO[50962:35319521] ? ?kind: 1

2016-07-04 19:20:47.938 testForKVO[50962:35319521] ? ?notificationIsPrior: 1

2016-07-04 19:20:47.938 testForKVO[50962:35319521] turn2

2016-07-04 19:20:47.938 testForKVO[50962:35319521] ? ?kind: 1

可以看到觀察被觸發(fā)4次,從turn0->turn1改變前后觸發(fā)2次咒劲,turn1->turn2改變前后觸發(fā)2次


其它


將options修改為 0 得到測試結(jié)果:

2016-07-04 19:50:43.925 testForKVO[51293:35351701] turn1

2016-07-04 19:50:43.925 testForKVO[51293:35351701] ? ?kind: 1

2016-07-04 19:50:43.925 testForKVO[51293:35351701] turn2

2016-07-04 19:50:43.925 testForKVO[51293:35351701] ? ?kind: 1


將options修改為

NSKeyValueObservingOptionNew|

NSKeyValueObservingOptionOld|

NSKeyValueObservingOptionInitial|

NSKeyValueObservingOptionPrior得到測試結(jié)果:

//注冊觀察服務(wù)時

2016-07-04 19:33:12.326 testForKVO[51133:35333070] turn0

2016-07-04 19:33:12.326 testForKVO[51133:35333070] ? ?kind: 1

2016-07-04 19:33:12.326 testForKVO[51133:35333070] ? ?new: turn0

//self.stringA=@"turn1";

2016-07-04 19:33:12.327 testForKVO[51133:35333070] turn0

2016-07-04 19:33:12.327 testForKVO[51133:35333070] ? ?kind: 1

2016-07-04 19:33:12.327 testForKVO[51133:35333070] ? ?old: turn0

2016-07-04 19:33:12.327 testForKVO[51133:35333070] ? ?notificationIsPrior: 1

2016-07-04 19:33:12.327 testForKVO[51133:35333070] turn1

2016-07-04 19:33:12.327 testForKVO[51133:35333070] ? ?kind: 1

2016-07-04 19:33:12.327 testForKVO[51133:35333070] ? ?old: turn0

2016-07-04 19:33:12.327 testForKVO[51133:35333070] ? ?new: turn1

//self.stringA=@"turn2";

2016-07-04 19:33:12.328 testForKVO[51133:35333070] turn1

2016-07-04 19:33:12.328 testForKVO[51133:35333070] ? ?kind: 1

2016-07-04 19:33:12.328 testForKVO[51133:35333070] ? ?old: turn1

2016-07-04 19:33:12.328 testForKVO[51133:35333070] ? ?notificationIsPrior: 1

2016-07-04 19:33:12.328 testForKVO[51133:35333070] turn2

2016-07-04 19:33:12.328 testForKVO[51133:35333070] ? ?kind: 1

2016-07-04 19:33:12.328 testForKVO[51133:35333070] ? ?old: turn1

2016-07-04 19:33:12.328 testForKVO[51133:35333070] ? ?new: turn2


參考資料:

ios里的KVO模式


00000002

最后編輯于
?著作權(quán)歸作者所有,轉(zhuǎn)載或內(nèi)容合作請聯(lián)系作者
  • 序言:七十年代末顷蟆,一起剝皮案震驚了整個濱河市诫隅,隨后出現(xiàn)的幾起案子,更是在濱河造成了極大的恐慌帐偎,老刑警劉巖逐纬,帶你破解...
    沈念sama閱讀 218,755評論 6 507
  • 序言:濱河連續(xù)發(fā)生了三起死亡事件,死亡現(xiàn)場離奇詭異削樊,居然都是意外死亡豁生,警方通過查閱死者的電腦和手機,發(fā)現(xiàn)死者居然都...
    沈念sama閱讀 93,305評論 3 395
  • 文/潘曉璐 我一進店門漫贞,熙熙樓的掌柜王于貴愁眉苦臉地迎上來甸箱,“玉大人,你說我怎么就攤上這事迅脐∩种常” “怎么了?”我有些...
    開封第一講書人閱讀 165,138評論 0 355
  • 文/不壞的土叔 我叫張陵谴蔑,是天一觀的道長豌骏。 經(jīng)常有香客問我,道長隐锭,這世上最難降的妖魔是什么窃躲? 我笑而不...
    開封第一講書人閱讀 58,791評論 1 295
  • 正文 為了忘掉前任,我火速辦了婚禮钦睡,結(jié)果婚禮上蒂窒,老公的妹妹穿的比我還像新娘。我一直安慰自己荞怒,他們只是感情好刘绣,可當我...
    茶點故事閱讀 67,794評論 6 392
  • 文/花漫 我一把揭開白布。 她就那樣靜靜地躺著挣输,像睡著了一般。 火紅的嫁衣襯著肌膚如雪福贞。 梳的紋絲不亂的頭發(fā)上撩嚼,一...
    開封第一講書人閱讀 51,631評論 1 305
  • 那天,我揣著相機與錄音挖帘,去河邊找鬼完丽。 笑死,一個胖子當著我的面吹牛拇舀,可吹牛的內(nèi)容都是我干的逻族。 我是一名探鬼主播,決...
    沈念sama閱讀 40,362評論 3 418
  • 文/蒼蘭香墨 我猛地睜開眼骄崩,長吁一口氣:“原來是場噩夢啊……” “哼聘鳞!你這毒婦竟也來了薄辅?” 一聲冷哼從身側(cè)響起,我...
    開封第一講書人閱讀 39,264評論 0 276
  • 序言:老撾萬榮一對情侶失蹤抠璃,失蹤者是張志新(化名)和其女友劉穎站楚,沒想到半個月后,有當?shù)厝嗽跇淞掷锇l(fā)現(xiàn)了一具尸體搏嗡,經(jīng)...
    沈念sama閱讀 45,724評論 1 315
  • 正文 獨居荒郊野嶺守林人離奇死亡窿春,尸身上長有42處帶血的膿包…… 初始之章·張勛 以下內(nèi)容為張勛視角 年9月15日...
    茶點故事閱讀 37,900評論 3 336
  • 正文 我和宋清朗相戀三年,在試婚紗的時候發(fā)現(xiàn)自己被綠了采盒。 大學時的朋友給我發(fā)了我未婚夫和他白月光在一起吃飯的照片旧乞。...
    茶點故事閱讀 40,040評論 1 350
  • 序言:一個原本活蹦亂跳的男人離奇死亡,死狀恐怖磅氨,靈堂內(nèi)的尸體忽然破棺而出尺栖,到底是詐尸還是另有隱情,我是刑警寧澤悍赢,帶...
    沈念sama閱讀 35,742評論 5 346
  • 正文 年R本政府宣布决瞳,位于F島的核電站,受9級特大地震影響左权,放射性物質(zhì)發(fā)生泄漏皮胡。R本人自食惡果不足惜,卻給世界環(huán)境...
    茶點故事閱讀 41,364評論 3 330
  • 文/蒙蒙 一赏迟、第九天 我趴在偏房一處隱蔽的房頂上張望屡贺。 院中可真熱鬧,春花似錦锌杀、人聲如沸甩栈。這莊子的主人今日做“春日...
    開封第一講書人閱讀 31,944評論 0 22
  • 文/蒼蘭香墨 我抬頭看了看天上的太陽量没。三九已至,卻和暖如春突想,著一層夾襖步出監(jiān)牢的瞬間殴蹄,已是汗流浹背。 一陣腳步聲響...
    開封第一講書人閱讀 33,060評論 1 270
  • 我被黑心中介騙來泰國打工猾担, 沒想到剛下飛機就差點兒被人妖公主榨干…… 1. 我叫王不留袭灯,地道東北人。 一個月前我還...
    沈念sama閱讀 48,247評論 3 371
  • 正文 我出身青樓绑嘹,卻偏偏與公主長得像稽荧,于是被迫代替她去往敵國和親。 傳聞我的和親對象是個殘疾皇子工腋,可洞房花燭夜當晚...
    茶點故事閱讀 44,979評論 2 355

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