とが利用できないNSNotification
ので、Swiftのオブザーバーをどこで削除する必要がありますか?viewDidUnload
dealloc()
回答:
と同じように機能する以下の方法を使用しますdealloc
。
deinit {
// Release all resources
// perform the deinitialization
}
デイニシャライザーは、クラスインスタンスの割り当てが解除される直前に呼び出されます。初期化子をinitキーワードで記述するのと同様に、初期化解除子をdeinitキーワードで記述します。デイニシャライザーは、クラスタイプでのみ使用できます。
deinit
メソッドは、ViewControllerBをプッシュするときに呼び出されません。
deinit
for ViewControllerAは、ナビゲーションコントローラーのスタックにない場合にのみ呼び出されます。たとえば:rootViewController(rootViewControllerがViewControllerAない場合)への切り替え
deinit
れない可能性が高くなります。電話をかけるのに理想的な場所func viewDidDisappear(_ animated: Bool)
以下のようiOSの9(およびOS X 10.11)、あなたはオブザーバーに削除する必要はありませんあなたはかかわらず、ブロックベースのオブザーバーを使用していない場合は、自分自身を。システムは、可能な場合、オブザーバーに対してゼロ化弱参照を使用するため、これを実行します。
また、ブロックベースのオブザーバーを使用している場合は、クロージャーのキャプチャリストを使用して自己を弱く[weak self]
キャプチャし、メソッドでオブザーバーを削除してくださいdeinit
。自己への弱い参照を使用しない場合deinit
、通知センターはそれへの強い参照を無期限に保持するため、メソッド(したがってそのオブザーバーの削除)が呼び出されることはありません。
詳細については、OS Xv10.11およびiOS9のFoundationリリースノートを参照してください。
オブザーバーをゼロ化弱参照として格納できる場合、基になるストレージはオブザーバーをゼロ化弱参照として格納します。または、オブジェクトを弱く格納できない場合(つまり、ランタイムを妨げるカスタムの保持/解放メカニズムがある場合)オブジェクトを弱く格納できることから)オブジェクトを弱でないゼロ参照として格納します。これは、オブザーバーが割り当て解除方法で登録を解除する必要がないことを意味します。
-[NSNotificationCenter addObserverForName:object:queue:usingBlock]メソッドを介したブロックベースのオブザーバーは、システムがこれらのオブザーバーへの強力な参照を保持しているため、使用されなくなったときに登録を解除する必要があります。
delegate = nil
はdealloc()
メソッドを書き込んでいました。これからも同じように動作しますか?
次の3つの方法を使用できます。
後popViewController
、戻る、navigationController
またはdismissViewControllerAnimated
:
deinit {
print("Remove NotificationCenter Deinit")
NSNotificationCenter.defaultCenter().removeObserver(self)
}
viewDidDisappear
、それがすでに次のビューコントローラになった後で削除します。
override func viewDidDisappear(animated: Bool) {
NSNotificationCenter.defaultCenter().removeObserver(self)
}
viewWillDisappear
-次のビューを開く前に:
override func viewWillDisappear(animated: Bool) {
NSNotificationCenter.defaultCenter().removeObserver(self)
}
Swift 3.0構文:
NotificationCenter.default.removeObserver(self)
Swift 4.2では、これはオブザーバーを削除する方法の1つです
deinit {
NotificationCenter.default.removeObserver(self, name: Notification.Name.Identifier, object: nil)
}
viewDidLoadクラスでaddObserver通知を設定します
override func viewDidLoad() {
super.viewDidLoad()
NotificationCenter.default.addObserver(self, selector: #selector(didReceivedItemDetail), name: Notification.Name.Identifier, object: nil)
}
Swiftは、クラスが破棄される前にクラスのインスタンスで呼び出されるdeinitメソッドを提供します。
また、この方法を使用する必要があることも指摘しておきます。
func addObserver(_ observer: Any, selector aSelector: Selector, name aName: NSNotification.Name?, object anObject: Any?)
の代わりに
func addObserver(forName name: NSNotification.Name?, object obj: Any?, queue: OperationQueue?, using block: @escaping (Notification) -> Void) -> NSObjectProtocol
後者はオブザーバーを削除しません(最近この問題に遭遇しました)。iOS9を使用している場合、前者はオブザーバーを削除します。
dealloc
。
deinit {
NotificationCenter.default.removeObserver(self)
}
スウィフト5
私はチャットアプリケーションを持っているので、ChatLogViewControllerから他のviewControllerに移動してから戻ってくるたびに、キーボード通知のオブザーバーが1つ追加されます。これを削除するには、viewControllerを変更するか、chatLogViewControllerから消えるときに、すべてのオブザーバーを削除します。
override func viewDidDisappear(_ animated: Bool) {
super.viewDidDisappear(animated)
NotificationCenter.default.removeObserver(self)
}