Tôi nên xóa trình quan sát NSNotification
ở đâu trong Swift, vì viewDidUnload
và dealloc()
không có sẵn?
Tôi nên xóa trình quan sát NSNotification
ở đâu trong Swift, vì viewDidUnload
và dealloc()
không có sẵn?
Câu trả lời:
Sử dụng phương pháp dưới đây có chức năng giống như dealloc
.
deinit {
// Release all resources
// perform the deinitialization
}
Một deinitializer được gọi ngay lập tức trước khi một cá thể lớp được phân bổ. Bạn viết deinitializers với từ khóa deinit, tương tự như cách intializers được viết với từ khóa init. Deinitializers chỉ có sẵn trên các loại lớp.
deinit
Phương thức @Kampai cho ViewControllerA sẽ không được gọi khi nó sẽ đẩy ViewControllerB.
deinit
đối với ViewControllerA sẽ chỉ được gọi khi nó không nằm trong ngăn xếp của bộ điều khiển điều hướng. Ví dụ: Chuyển sang rootViewController (nếu rootViewController không phải là ViewControllerA)
deinit
. Nơi lý tưởng để cuộc gọi sẽfunc viewDidDisappear(_ animated: Bool)
Kể từ iOS 9 (và OS X 10.11), bạn không cần phải tự mình xóa người quan sát , nếu bạn không sử dụng trình quan sát dựa trên khối. Hệ thống sẽ làm điều đó cho bạn, vì nó sử dụng các tham chiếu yếu cho người quan sát, nếu nó có thể.
Và nếu bạn đang sử dụng trình quan sát dựa trên khối, hãy đảm bảo rằng bạn tự nắm bắt yếu bằng cách sử dụng [weak self]
trong danh sách nắm bắt của đóng và loại bỏ trình quan sát trong deinit
phương pháp. Nếu bạn không sử dụng tham chiếu yếu cho bản thân, deinit
phương thức (và do đó xóa người quan sát đó) sẽ không bao giờ được gọi vì Trung tâm thông báo sẽ giữ một tham chiếu mạnh đến nó vô thời hạn.
Có thể tìm thấy thêm thông tin tại Ghi chú phát hành Foundation cho OS X v10.11 và iOS 9 .
Nếu người quan sát có thể được lưu trữ dưới dạng tham chiếu yếu 0 thì bộ lưu trữ bên dưới sẽ lưu người quan sát dưới dạng tham chiếu yếu 0, hoặc nếu đối tượng không thể được lưu trữ yếu (tức là nó có cơ chế giữ lại / giải phóng tùy chỉnh sẽ ngăn thời gian chạy từ khả năng lưu trữ đối tượng yếu) nó sẽ lưu trữ đối tượng dưới dạng tham chiếu zeroing không yếu. Điều này có nghĩa là người quan sát không bắt buộc phải hủy đăng ký trong phương thức phân bổ của họ.
Những người quan sát dựa trên khối thông qua phương thức - [NSNotificationCenter addObserverForName: object: queue: usingBlock] vẫn cần được hủy đăng ký khi không còn được sử dụng vì hệ thống vẫn giữ một tham chiếu mạnh mẽ đến những người quan sát này.
delegate = nil
bằng dealloc()
phương pháp. Nó có hoạt động như nhau từ bây giờ không?
Bạn có thể sử dụng ba phương pháp:
sau popViewController
, trở lại navigationController
hoặc dismissViewControllerAnimated
:
deinit {
print("Remove NotificationCenter Deinit")
NSNotificationCenter.defaultCenter().removeObserver(self)
}
viewDidDisappear
, xóa sau khi nó đã là bộ điều khiển chế độ xem tiếp theo:
override func viewDidDisappear(animated: Bool) {
NSNotificationCenter.defaultCenter().removeObserver(self)
}
viewWillDisappear
- trước khi mở chế độ xem tiếp theo:
override func viewWillDisappear(animated: Bool) {
NSNotificationCenter.defaultCenter().removeObserver(self)
}
Cú pháp Swift 3.0:
NotificationCenter.default.removeObserver(self)
Trong Swift 4.2, đây là một trong những cách bạn có thể xóa trình quan sát
deinit {
NotificationCenter.default.removeObserver(self, name: Notification.Name.Identifier, object: nil)
}
thiết lập thông báo addObserver trong lớp viewDidLoad
override func viewDidLoad() {
super.viewDidLoad()
NotificationCenter.default.addObserver(self, selector: #selector(didReceivedItemDetail), name: Notification.Name.Identifier, object: nil)
}
Swift cung cấp một phương thức deinit được gọi trên các thể hiện của các lớp trước khi chúng bị hủy.
Tôi cũng muốn chỉ ra rằng bạn nên sử dụng phương pháp này:
func addObserver(_ observer: Any, selector aSelector: Selector, name aName: NSNotification.Name?, object anObject: Any?)
Thay vì
func addObserver(forName name: NSNotification.Name?, object obj: Any?, queue: OperationQueue?, using block: @escaping (Notification) -> Void) -> NSObjectProtocol
Sau này sẽ không loại bỏ người quan sát (Gần đây Ran có vấn đề này). Trước đó sẽ xóa trình quan sát nếu bạn đang sử dụng iOS9.
dealloc
phương pháp.
deinit {
NotificationCenter.default.removeObserver(self)
}
Cũng tốt nếu bạn thêm người quan sát của mình vào viewWillAppear()
và xóa họ trongviewWillDisappear()
Swift 5
Tôi có một ứng dụng trò chuyện, vì vậy bất cứ khi nào tôi chuyển từ ChatLogViewController của mình sang một số viewController khác và sau đó quay lại, tôi có thêm 1 Observer thông báo bàn phím của mình. Để loại bỏ điều đó, tôi xóa tất cả những người quan sát khi tôi thay đổi viewController hoặc biến mất khỏi chatLogViewController của mình .
override func viewDidDisappear(_ animated: Bool) {
super.viewDidDisappear(animated)
NotificationCenter.default.removeObserver(self)
}