我正在尝试从v2的coinmarketcap API导入JSON数据。我让它与v1一起工作,因为它是一个数组,但是新版本是字典,我无法完全理解我的结构。
我使用的API是:https://api.coinmarketcap.com/v2/ticker/?convert=AUD
我的结构设置如下:
struct Coin: Decodable {
private enum CodingKeys: String, CodingKey {
case id = "rank", symbol, name, priceAUD = "quotes"
}
var id: String
var symbol : String
var name : String
var priceAUD : quoteStruct
}
struct quoteStruct{
let aud : priceStruct
}
struct priceStruct{
let price : String
}
我获取数据的代码是:
var coins = [Coin]()
func getCoinData() {
let jsonURL = "https://api.coinmarketcap.com/v2/ticker/?convert=AUD"
let url = URL(string: jsonURL)
URLSession.shared.dataTask(with: url!) { [unowned self] (data, response, error) in
guard let data = data else { return }
do {
self.coins = try JSONDecoder().decode([Coin].self, from: data)
DispatchQueue.main.async {
self.tableView.reloadData()
}
} catch {
print("Error is : \n\(error)")
}
}.resume()
}
我获取数据的代码与以前使用该API v1时使用的代码相同,但是我认为我没有正确构建结构。
提前致谢!
最佳答案
您在data
参数中响应的应该是数组而不是字典。您将无法在未定义的键上迭代字典。最好先更新您的API响应。
但是,如果您希望继续现有的API响应,则首先需要将响应转换为数组,并使用Decodable
结构为:
struct Coin: Decodable {
var id: String
var symbol : String
var name : String
var priceAUD : QuoteStruct
private enum CodingKeys: String, CodingKey {
case id = "rank", symbol, name, priceAUD = "quotes"
}
}
struct QuoteStruct: Decodable {
let aud : PriceStruct
}
struct PriceStruct: Decodable {
let price : String
}
将您在API块中的数据解析更新为:
guard let responseData = data else { return }
do {
let json = try? JSONSerialization.jsonObject(with: responseData, options: [])
if let jsonData = json as? [String: Any], let dataObject = jsonData["data"] as? [Int: Any] {
let coinArray = dataObject.map { $0.1 }
if let jsonData = try? JSONSerialization.data(withJSONObject: coinArray, options: .prettyPrinted) {
coins = try JSONDecoder().decode([Coin].self, from: jsonData)
DispatchQueue.main.async {
self.tableView.reloadData()
}
}
}
} catch {
print("Error is : \n\(error)")
}
关于ios - Swift中嵌套字典API的结构,我们在Stack Overflow上找到一个类似的问题:https://stackoverflow.com/questions/50364468/