[英]check the json response is array or int or string for a key?
我有 json 響應,其中“產品”鍵有時具有 int 值,在某些情況下它有一個數組? 如何檢查它是否具有數組或 Int?
"products": 25
或者
"products": [77,80,81,86]
我正在使用這個
self.productsCount = mResp["products"] as! [Int]
但是每次沒有數組時它都會崩潰。
現在我不知道如何檢查這個,因為我有不同的 Int 和 Array 選項?
請幫助我。謝謝
它崩潰是因為你強制解包為一個整數數組,即使你只有一個整數。 解決方案是檢查兩者:
self.productsCount = mResp["products"] as? [Int] ?? mResp["products"] as? Int
其他解決方案
if let proCount = mResp["products"] as? [Int] {
self.productsCount = proCount
} else {
self.productsCount = mResp["products"] as? Int
}
這里沒有必要回退到Any
。 甚至像這樣有問題的 JSON 也可以使用Codable
處理。 您只需要繼續嘗試不同的類型,直到其中一種有效。
struct Thing: Decodable {
let products: [Int]
enum CodingKeys: String, CodingKey {
case products
}
init(from decoder: Decoder) throws {
// First pull out the "products" key
let container = try decoder.container(keyedBy: CodingKeys.self)
do {
// Then try to decode the value as an array
products = try container.decode([Int].self, forKey: .products)
} catch {
// If that didn't work, try to decode it as a single value
products = [try container.decode(Int.self, forKey: .products)]
}
}
}
let singleJSON = Data("""
{ "products": 25 }
""".utf8)
let listJSON = Data("""
{ "products": [77,80,81,86] }
""".utf8)
let decoder = JSONDecoder()
try! decoder.decode(Thing.self, from: singleJSON).products // [25]
try! decoder.decode(Thing.self, from: listJSON).products // [77, 80, 81, 86]
這是您想要的臨時解決方案。 使用“任何”類型檢查可能的類型。
var anyType : Any!
anyType = "123"
anyType = ["Test","Test1"]
anyType = 1
if anyType is Array {
print("is Array")
}else if anyType is String {
print("is String")
}else if anyType is Int {
print("is Int")
}
假設您的 json 名稱是jsonData
檢查Int
和Array Int
:
if let intVal = jsonData["products"] as? Int {
print("Products is a Integer: ", intVal)
} else if let jsonArr = jsonData["products"] as? [Int] {
var intVals = [Int]()
for json in jsonArr {
intVals.append(json)
}
print("Json is array of Int: ", intVals)
}
let dict = [77,80,81,86]//Pass your parameter or parsed json value
if dict is Array<Any> {
print("Yes, it's an Array")
}
else{
print("NO, it's not an Array")
}
通用解決方案是這樣的,
let products = mResp["products"] as? Any
if let item = products as? [Int] {
print("array", item)
} else if let item = products as? Int {
print("Integer", item)
}
使用Generics
以獲得更好的解決方案並在解碼此模型時提供類型。
struct Product<T: Codable>: Codable {
let products: T?
}
您可以將它與嵌套的try catch
一起使用:
do {
let product = try JSONDecoder().decode(Product<Int>.self, from: data)
print(product)
} catch {
do {
let product = try JSONDecoder().decode(Product<[Int]>.self, from: data)
print(product)
} catch {
print(error)
}
}
注意:此解決方案假定可編碼結構中不超過幾個不同的類型變化屬性。 如果有多個類型不同的屬性,我建議使用接受的答案中提供的自定義init(decoder:)
,這將是更好的設計,而不是使用try-catch
樹。
聲明:本站的技術帖子網頁,遵循CC BY-SA 4.0協議,如果您需要轉載,請注明本站網址或者原文地址。任何問題請咨詢:yoyou2525@163.com.