[英]KVO and Swift 3.0: How to evaluate the change dictionary?
我試圖弄清楚如何評估func observeValue(forKeyPath...
的[NSKeyValueChangeKey : AnyObject]
更改字典參數func observeValue(forKeyPath...
我在操場上有以下代碼,我正在評估更改字典的方式我總是想到更改是NSKeyValueChange.setting(這絕對是錯誤的)。
評估變更字典的正確方法是什么?
import Foundation
class KVOTester: NSObject {
dynamic var items = [Int]() // Observe via KVO
override init() {
super.init()
self.addObserver(self, forKeyPath: #keyPath(KVOTester.items), options: [], context: nil)
}
deinit {
self.removeObserver(self, forKeyPath: #keyPath(KVOTester.items))
}
func exerciseKVO() {
self.items = [Int]() // NSKeyValueChange.setting
self.items.append(1) // NSKeyValueChange.insertion
self.items[0] = 2 // NSKeyValueChange.replacement
self.items.remove(at: 0) // NSKeyValueChange.removal
}
override func observeValue(forKeyPath keyPath: String?, of object: AnyObject?, change: [NSKeyValueChangeKey : AnyObject]?, context: UnsafeMutablePointer<Void>?) {
// We are only interested in changes to our items array
guard keyPath == "items" else { return }
// #1: object is the KVOTester instance - why isn't it the items array?
// #2 I don't understand how to use the change dictionary to determine what type of change occurred. The following
// is wrong - it *always* prints "Setting".
if let changeKindValue = change?[.kindKey] as? UInt, changeType = NSKeyValueChange(rawValue: changeKindValue) {
switch changeType {
case .setting:
print("Setting")
break
case .insertion:
print("Insertion")
break
case .removal:
print("Removal")
break
case .replacement:
print("Replacement")
break
}
}
}
}
let kvoTester = KVOTester()
kvoTester.exerciseKVO()
正如原始提問者在評論中指出的那樣,以下代碼將給出預期結果:
import Foundation
class KVOTester: NSObject {
dynamic var items = [Int]() // Observe via KVO
override init() {
super.init()
self.addObserver(self, forKeyPath: #keyPath(KVOTester.items), options: [], context: nil)
}
deinit {
self.removeObserver(self, forKeyPath: #keyPath(KVOTester.items))
}
func exerciseKVO() {
let kvoArray = self.mutableArrayValue(forKey: #keyPath(KVOTester.items))
items = [Int]() // NSKeyValueChange.setting
kvoArray.add(1) // NSKeyValueChange.insertion
kvoArray.replaceObject(at: 0, with: 2) // NSKeyValueChange.replacement
kvoArray.removeObject(at: 0) // NSKeyValueChange.removal
}
override func observeValue(forKeyPath keyPath: String?, of object: Any?, change: [NSKeyValueChangeKey : Any]?, context: UnsafeMutableRawPointer?) {
// We are only interested in changes to our items array
guard keyPath == "items" else { return }
if let changeKindValue = change?[.kindKey] as? UInt,
let changeType = NSKeyValueChange(rawValue: changeKindValue) {
switch changeType {
case .setting:
print("Setting")
break
case .insertion:
print("Insertion")
break
case .removal:
print("Removal")
break
case .replacement:
print("Replacement")
break
}
}
}
}
let kvoTester = KVOTester()
kvoTester.exerciseKVO()
聲明:本站的技術帖子網頁,遵循CC BY-SA 4.0協議,如果您需要轉載,請注明本站網址或者原文地址。任何問題請咨詢:yoyou2525@163.com.