2008-08-17 19 views

回答

38

您需要使用-removeObserver:forKeyPath:-[NSObject dealloc]運行之前刪除觀察者,所以是的,在您班級的-dealloc方法中可以使用。

更好的是,雖然會有一個確定性點,凡是擁有正在進行觀察的對象都可以告訴它已完成並將最終解除分配。這樣,當不再需要觀察事物時,不管何時實際釋放,都可以立即停止觀察。

要記住這一點很重要,因爲可可中的對象的生命週期並不像某些人認爲的那樣確定。各種各樣的Mac OS X框架本身發送您的對象-retain-autorelease,延長他們的生活超出你可能會認爲它會。此外,當您轉換到Objective-C垃圾回收時,您會發現-finalize將在非常不同的時間運行 - 並且在非常不同的環境中運行 - 比-dealloc的運行時間更長。一方面,最終確定發生在另一個線程上,所以你真的不能將安全地發送到-finalize方法中的另一個對象。

棒內存(和其他稀缺資源)管理-dealloc-finalize,並使用單獨的-invalidate方法有一個業主告訴你在一個確定的點用它做一個對象;做一些事情,比如去除那裏的KVO觀察。你的代碼的意圖會更清晰,你將會減少微妙的錯誤來照顧。

+7

我可以從經驗中確認您將獲得無窮的崩潰,如果不刪除你的觀察員的痛苦。 – Jeff 2010-04-28 23:33:17

+0

感謝您的詳細解釋! – 2011-08-31 10:56:52

5

我通過痛苦的體驗獲得了一些額外的信息:雖然NSNotificationCenter在垃圾回收下運行時使用了零引用弱引用,但KVO卻沒有。因此,您可以避免在使用GC時不移除NSNotificationCenter觀察者(使用保留/釋放時,仍需要移除觀察者),但仍必須移除KVO觀察者,如Chris所述。

2

肯定與克里斯同意「堅持記憶(和其他稀缺資源)管理在-dealloc和-finalize ...」評論。很多時候,我會看到人們嘗試在其dealloc函數中使NSTimer對象無效。問題是,NSTimer保留它的目標。所以,如果NSTimer的目標是自己的,dealloc將永遠不會被調用,導致一些潛在的令人討厭的內存泄漏。

的invalidate -invalidate和做其他內存清理你的deallocfinalize.

相關問題