我想提取struct
中的字段的列表,只用Type
对象。
public struct CoordinateData: Codable {
var longitude: Double?
var latitude: Double?
}
我收到Codable.Type
(在此阶段,我不知道对象是CoordinateData
,并且我想使我的解决方案对任何Codable
都是通用的)我想提取[“经度”,“纬度”]([String]
)
我尝试使用Mirror
,当我知道对象的确切类型以及该类型为空的初始值设定项时,它就会起作用:
let metatype: CoordinateData.Type = CoordinateData.self
let c3 = metatype.init()
let m3 = Mirror(reflecting: c3)
for (property, value) in m3.children {
guard let property = property else {
print("no proeprty")
continue
}
print(property)
}
但是当我只有Codable.Type
时此解决方案不起作用,因为它只有一个.init()
方法期望我没有的解码器.init(from: Decoder)
。
有任何建议吗?
这可能有效,但是您需要考虑一些事项。
func mirror<T: Any>(object: T) {
let c3 = object
let m3 = Mirror(reflecting: c3)
for (property, _) in m3.children {
guard let property = property else {
print("no proeprty")
continue
}
print(property)
}
}
使用:mirror(object: CoordinateData())
mirror(object: Foo())
您总是需要传递一个初始化的对象。
这将消除函数的初始化责任,因为据我所知,您不能初始化通用对象,因为它们是通用的。
因此,通过传递对象本身,这将为您工作。
更新:由于没有显式的结构类型参数,也可能会被滥用,但传递不是对象的任何参数将不会产生任何结果,这可以通过将结构更改为类并将<T>
传递为[ C0]。
您也可以以这种方式执行此操作,因为<T: AnyObject>
参数已经是Mirror
类型,所以我们可以扩展Any
它本身以在下面进行Mirror
功能检查。
getProperties()
用法: extension Mirror {
func getProperties() -> [String] {
self.children.compactMap { child in
guard let property = child.label else {
return nil
}
return property
}
}
}
这将始终为您提供一个字符串数组,但是,如果没有属性,它将返回一个空数组。