对于来自Objective-C解析器的JSON字典,Swift泛型不能像预期的那样工作
我有一个从JSON字典中检索非可选值的函数。 如果字典中没有值或值的类型错误,则需要3个参数:dictionary、key和default值对于来自Objective-C解析器的JSON字典,Swift泛型不能像预期的那样工作,objective-c,json,swift,generics,Objective C,Json,Swift,Generics,我有一个从JSON字典中检索非可选值的函数。 如果字典中没有值或值的类型错误,则需要3个参数:dictionary、key和default值 func valueFromJSONDict<T>(dict:[NSObject: AnyObject]?, key: NSObject, defaultValue: T) -> T { if let value = dict?[key] as? T { return value } return
func valueFromJSONDict<T>(dict:[NSObject: AnyObject]?, key: NSObject, defaultValue: T) -> T {
if let value = dict?[key] as? T {
return value
}
return defaultValue
}
但如果我在没有泛型的情况下做同样的事情,它会很好:
title = { () -> String
if let value = dict?["title"] as? String {
title = value
} else {
return ""
}
}()
这个解析后的JSON dict来自Objective-C解析器,如果我打印dict中的值的dynamicType类似于_CFNSString,但是T.self是Swift.String,所以Swift可能无法识别类型
如何使其工作?您的dict对象看起来像什么
以下是我的建议:
typealias JSONObject = [String: AnyObject]
func valueFromJSON<T>(json: JSONObject?, key: String, defaultValue: T) -> T
{
if let value = json?[key] as? T {
return value
}
return defaultValue
}
let json = ["Name": "Sir Lancelot",
"Quest": "To seek the Holy Grail",
"Favorite Color": "Blue..."]
let name = valueFromJSON(json, "Name", "Sir Not Appearing In This Film")
我发现,这种方法的实际工作原理是我将结果分配给某个var或let: 但如果我将结果指定给属性,则不起作用:
最后,我通过将属性类型从非可选的@NSManaged var title:String替换为隐式展开的可选@NSManaged var title:String,解决了这个问题 关于代码风格的好建议,我一定会使用它。但是这里的键类型没有意义。我认为问题在于JSON来自Objective-C解析器,因此Swift无法正常识别类型。您可能是对的,但在不知道dict内容的情况下很难进行测试。此外,我建议尽可能多地使用Swift类型String、Int、Float等。。。而不是Obj-C对应物。我认为Swift有更好的转换/桥接逻辑和它自己的原生类型。同意,但这篇文章来自AFNetworking,它是Objective-C。
typealias JSONObject = [String: AnyObject]
func valueFromJSON<T>(json: JSONObject?, key: String, defaultValue: T) -> T
{
if let value = json?[key] as? T {
return value
}
return defaultValue
}
let json = ["Name": "Sir Lancelot",
"Quest": "To seek the Holy Grail",
"Favorite Color": "Blue..."]
let name = valueFromJSON(json, "Name", "Sir Not Appearing In This Film")
let value = valueFromJSONDict(dict, "title", "") // value from JSON
title = valueFromJSONDict(dict, "title", "") // always ""