Swift 4中如何使用KeyPath引用对象自身?
Swift 4 KeyPath 引用对象自身的实现方案
嘿,这个问题我之前在项目里也遇到过!确实Swift 4原生的KeyPath语法没法直接指向对象本身——毕竟KeyPath设计的初衷是用来定位对象的属性,而对象自身并不属于“属性”范畴,但咱们可以通过几个巧妙的方式来实现类似需求,甚至还挺简便的。
方法一:通用KeyPath扩展(推荐)
给KeyPath添加一个静态的identity属性,专门用来表示“对象自身”的KeyPath,这样所有类型都能直接复用:
extension KeyPath where Root == Value { static var identity: Self { return \Root.self } }
使用示例
比如你有一个User类,想要用KeyPath获取对象本身:
class User { let name: String init(name: String) { self.name = name } } let user = User(name: "Charlie") // 使用自定义的identity KeyPath获取对象自身 let sameUser = user[keyPath: KeyPath<User, User>.identity] // 或者更简洁的写法(Swift会自动推断类型) let sameUser2 = user[keyPath: \.identity]
方法二:针对特定类型定义静态KeyPath
如果只需要在某个特定类型里使用,也可以直接在类型内部定义专属的identity KeyPath:
class User { let name: String init(name: String) { self.name = name } // 定义指向自身的KeyPath static let identity: KeyPath<User, User> = \User.self }
使用示例
let users = [User(name: "Alice"), User(name: "Bob")] // 用map结合identity KeyPath,得到原数组的副本(元素完全相同) let sameUsers = users.map { $0[keyPath: User.identity] }
方法三:全局工具函数
如果不想写扩展,也可以定义一个全局的工具函数来生成identity KeyPath:
func identityKeyPath<T>() -> KeyPath<T, T> { return \T.self }
使用示例
let string = "Hello" let sameString = string[keyPath: identityKeyPath<String>()]
补充说明
其实很多场景下,如果只是需要“获取对象自身”的逻辑,也可以直接用闭包代替KeyPath(比如{ $0 }),但如果你的代码架构必须依赖KeyPath类型(比如某些响应式框架、数据映射工具的要求),上面的几种KeyPath实现方式就完全能满足需求。
内容的提问来源于stack exchange,提问作者bteapot
相关产品推荐
相关产品推荐

