在Swift 4中,许多基金会团队已经讨论过与Swift 3相比,使用keyPaths要容易得多。这就引出了一个问题......什么是keyPath?说真的,我找不到任何明确的资源。
答案 0 :(得分:13)
Objective-C能够动态引用属性而不是直接引用属性。这些引用称为keypaths。它们与直接属性访问不同,因为它们实际上不会读取或写入值,它们只是将其存放起来以供使用。
让我们定义一个名为Cavaliers的结构和一个名为Player的结构,然后创建每个结构的一个实例:
// an example struct
struct Player {
var name: String
var rank: String
}
// another example struct, this time with a method
struct Cavaliers {
var name: String
var maxPoint: Double
var captain: Player
func goTomaxPoint() {
print("\(name) is now travelling at warp \(maxPoint)")
}
}
// create instances of those two structs
let james = Player(name: "Lebron", rank: "Captain")
let irving = Cavaliers(name: "Kyrie", maxPoint: 9.975, captain: james)
// grab a reference to the `goTomaxPoint()` method
let score = irving.goTomaxPoint
// call that reference
score()
最后一行创建了一个名为score的goTomaxPoint()方法的引用。问题是,我们无法创建对队长名称属性的引用,但keypath可以这样做。
let nameKeyPath = \Cavaliers.name
let maxPointKeyPath = \Cavaliers.maxPoint
let captainName = \Cavaliers.captain.name
let cavaliersName = irving[keyPath: nameKeyPath]
let cavaliersMaxPoint = irving[keyPath: maxPointKeyPath]
let cavaliersNameCaptain = irving[keyPath: captainName]
请使用Xcode 9或快照进行测试。
答案 1 :(得分:0)
Swift KVC
KeyPath
是对类型的属性而非值的引用。它为语言增添了活力
其中有一些:
KeyPath<Root, Value>
- 只读WritableKeyPath<Root, Value>
- var
属性的读/写ReferenceWritableKeyPath<Root, Value>
- 仅对引用类型进行读/写[About]PartialKeyPath<Root>
AnyKeyPath
你会发现 KeyPath
用于快捷方式(例如排序、迭代、过滤)、KVO[Example]、MemoryLayout[Example]、SwiftUI 和其他更高级的功能
语法
class SomeClass {
var v: String = "Hello World"
}
Pre Swift v4 - 速度慢且类型不安全
@objc //For example var v: String = "Hello world"
let keyPath = #keyPath(SomeClass.v) //keyPath is String Type
//read
someClass.value(forKeyPath: keyPath) //or forKey:
//write
someClass.setValue("Another string", forKeyPath: keyPath) //or forKey:
\
开始let someKeyPath = \SomeClass.v //KeyPath<SomeClass, String>
\.
someClass.observe(\.v, options: .new) //someClass1.v
//read
let res = someClass[keyPath: \SomeClass.v]
//write
someClass[keyPath: \.v] = "Another string"