私は(addObserverを使用して:...)別のオブジェクトバーからKVO通知を受信するオブジェクトFOOを登録した私は、FOOを解放した場合、私はバーにremoveObserver:forKeyPath:
メッセージを送信する必要があります-deallocで?Cocoaでは、オブジェクトの割り当てを解除するときに、KVO通知を受け取るオブジェクトを削除する必要がありますか?
答えて
-[NSObject dealloc]
が実行される前に、オブザーバを削除する必要があります。そうすれば、クラスの-dealloc
メソッドで実行することができます。
それよりも優れていますが、観測を行っているオブジェクトを所有しているものは、それが完了したことを示すことができ、(最終的に)割り当てを解除されるという決定論的な点があるでしょう。そうすることで、実際に割り当てを解除した時点に関係なく、観測を行うことがもう必要なくなったときにすぐに観察を停止することができます。
これは、ココアのオブジェクトの存続期間が、それがあると思われるように決定的ではないため、留意することが重要です。さまざまなMac OS Xのフレームワーク自体は、あなたのオブジェクト-retain
と-autorelease
を送り、そうでないと思われるかもしれない寿命を延ばします。
さらに、Objective-Cガベージコレクションに移行すると、-finalize
は非常に異なる時刻に(非常に異なるコンテキストで)、-dealloc
よりも実行されることがわかります。一つは、ファイナライズは別のスレッドで行われるので、実際にはできません-removeObserver:forKeyPath:
を別のオブジェクトに-finalize
メソッドで安全に送信できません。 -dealloc
と-finalize
におけるメモリ(および他の希少資源)へ
スティック管理、および所有者は、あなたが、確定時点でそれで行われているオブジェクトを伝える持っている別の-invalidate
メソッドを使用します。 KVOの観測結果を削除するようなことをしてください。コードの意図が明確になり、微妙なバグが少なくなります。
私は苦しい経験から得た追加情報:ガベージコレクションの実行中にNSNotificationCenterが弱参照をゼロにしていますが、KVOはそうではありません。したがって、GCを使用しているときにNSNotificationCenterオブザーバを削除しなくても済むようにすることができます(ただし、retain/releaseを使用する場合は、オブザーバを削除する必要があります)が、KVOオブザーバは削除する必要があります。
これはどこかに書かれていますか? – hpique
Chrisは、「メモリとその他の乏しいリソースに管理してください。」という-deallocと-finalizeの管理に関するコメントにはっきりと同意します。何度も、dealloc関数でNSTimerオブジェクトを無効にしようとする人がいます。問題は、NSTimerがターゲットを保持していることです。したがって、NSTimerのターゲットが自己であれば、deallocは呼び出されることはありません。その結果、メモリリークが発生する可能性があります。
-invalidate
での無効化と私は経験から、あなたのオブザーバーを削除しない場合は、無限のクラッシュに届きます痛みを確認することができ、あなたのdealloc
とfinalize.
- 1. gcnewに割り当てられたオブジェクトでは、いつ削除する必要がありますか?
- 2. 削除後にポインタ0を割り当てる必要がありますか?
- 3. ARCがオブジェクトを割り当て解除するのはなぜですか?
- 4. UIApplicationDelegateが所有するオブジェクトの割り当てを解除する利点はありますか?
- 5. 他のオブジェクトを参照に割り当てる前にインスタンスオブジェクトを解放する必要はありますか?
- 6. オブジェクトが不思議に割り当て解除される
- 7. オブジェクトが孤立する前にオブジェクトからイベントサブスクリプションを削除する必要はありますか?
- 8. 新しいオブジェクトを挿入する前にリストからオブジェクトを削除する必要がありますか?
- 9. C#Windows 7でアプリケーションを削除するときに通知を受け取ります
- 10. iOS:オブジェクトをプロパティリスナーとして追加するとき、オブジェクトを解放する前にリスナーを「登録解除」する必要がありますか?
- 11. 割り当て/割り当て解除を追跡できますか?
- 12. いつオブザーバーを削除すればよいですか?オブザーバを削除する前にオブジェクトの割り当てを解除する際のエラー
- 13. オブジェクトの割り当てが解除されます - なぜですか?どこ?
- 14. 要素を削除する前にjqueryイベントのバインドを解除する必要がありますか?
- 15. オブジェクトが破壊されたときにオブザーバを削除する必要がありますか?
- 16. GLSurfaceViewでテクスチャを削除する必要がありますか?
- 17. リストボックスにアイテムが削除されたときに通知を受け取りますか?
- 18. オブジェクトが実際に割り当てられたことを確認する必要がありますか?
- 19. C++オブジェクトへのポインタの2次元配列の割り当てを解除し、削除する方法
- 20. Protobuf:set_allocated_ *は割り当てられたオブジェクトを削除しますか?
- 21. 動的配列から要素を削除するときにmemmoveの後で再割り当てする必要はありますか?
- 22. mapStateToPropsはオブジェクトを返す必要があります。代わりにMap {}を受け取りましたか?
- 23. NSMutableArrayのオブジェクトを解放する必要がありますか?
- 24. なぜオブジェクトを割り当てて、インスタンス変数をObj-Cで設定する必要がありますか?
- 25. 仮想インデックスを削除する必要がありますか?
- 26. QUpdSocketsを削除する必要がありますか?
- 27. イベントハンドラを削除する必要がありますか?
- 28. System.Windows.Media.Penを削除する必要がありますか?
- 29. OOP - 投稿を削除する必要がありますか?
- 30. コールバックを持つ別のオブジェクトが所有するオブジェクトを、削除するオブジェクトから削除できますか?
に他のメモリクリーンアップを行います。 – Jeff
その徹底的な説明をありがとう! OS X 10.7ライオンのよう –
は、-removeObserver 'もあります:forKeyPathは:コンテキスト:'、あなたが-addObserver 'に渡された同じコンテキストに渡すことができます:forKeyPath:オプション:コンテキスト:'。ユニークなコンテキストを渡すことで、あなたがあなたを削除したときに他人の観察を削除しないようにします。 –