类型不匹配 Swift JSON

Posted

技术标签:

【中文标题】类型不匹配 Swift JSON【英文标题】:Type Mismatch Swift JSON 【发布时间】:2020-08-30 18:07:32 【问题描述】:

我认为我正确地创建了结构,但它给出了错误。

typeMismatch(Swift.Array, Swift.DecodingError.Context(codingPath: [], debugDescription: "期望解码 Array 但找到了一个字典。", underlyingError: nil))

型号:

struct veriler : Codable 
    let success : Bool
    let result : [result]
    


struct result : Codable 
    let country : String
    let totalCases : String
    let newCases : String
    let totalDeaths : String
    let newDeaths : String
    let totalRecovered : String
    let activeCases : String

JSON 数据:


  "success": true,
  "result": [
    
      "country": "China",
      "totalcases": "80,881",
      "newCases": "+21",
      "totaldeaths": "3,226",
      "newDeaths": "+13",
      "totalRecovered": "68,709",
      "activeCases": "8,946"
    ,
    
      "country": "Italy",
      "totalcases": "27,980",
      "newCases": "",
      "totaldeaths": "2,158",
      "newDeaths": "",
      "totalRecovered": "2,749",
      "activeCases": "23,073"
    ,
    "..."
  ]

解码:

let decoder = JSONDecoder()
        do 
            let country = try decoder.decode([result].self, from: data!)
          for i in 0..<country.count 
            print (country[i].country)
          
         catch 
          print(error)
        

【问题讨论】:

为什么不用veriler.self 而不是[result].self!? 【参考方案1】:

首先您需要通过指定自定义CodingKeys 来修改result 结构(注意模型中的totalCases 和JSON 中的totalcases 之间的不匹配):

struct result: Codable 
    enum CodingKeys: String, CodingKey 
        case country, newCases, newDeaths, totalRecovered, activeCases
        case totalCases = "totalcases"
        case totalDeaths = "totaldeaths"
    
    
    let country: String
    let totalCases: String
    let newCases: String
    let totalDeaths: String
    let newDeaths: String
    let totalRecovered: String
    let activeCases: String

那么你需要解码veriler.self而不是[result].self

let decoder = JSONDecoder()
do 
    let result = try decoder.decode(veriler.self, from: data!)
    let countries = result.result
    for i in 0 ..< countries.count 
        print(countries[i].country)
    
 catch 
    print(error)

注意:我建议遵循 Swift 指南并命名结构,例如 ResultVeriler(只有实例应该是小写的)。

【讨论】:

出现此错误。 keyNotFound(CodingKeys(stringValue: "totalcases", intValue: nil), Swift.DecodingError.Context(codingPath: [CodingKeys(stringValue: "result", intValue: nil), _JSONKey(stringValue: "Index 0", intValue: 0) ], debugDescription: "No value associated with key CodingKeys(stringValue: \"totalcases\", intValue: nil) (\"totalcases\").", underlyingError: nil)) 您是否在问题中的 JSON 上尝试过此代码?因为在你的问题中我可以清楚地看到totalcases。确保您在实际 JSON 中有相同的字段。如果不只是调整 CodingKeys。 @E.YILDIRIM 如果您可以确认问题中的 JSON 与您尝试解析的 完全相同 JSON,则无需。否则,您可以使用实际的 JSON 更新问题。 @E.YILDIRIM 然后您在问题中发布了错误的 JSON。尝试使用我的答案,但没有 CodingKeys 枚举,它应该可以工作。 当我更改他们的名字时它起作用了 (totalCases , totalDeaths) 。该网站给出的样本名称是错误的。所以它不是起源于我们。感谢您的所有帮助:)

以上是关于类型不匹配 Swift JSON的主要内容,如果未能解决你的问题,请参考以下文章

Swift JSON 序列化类型不匹配

Swift 3:NSArray 元素无法匹配 Swift Array 元素类型

协议中的 Swift 协议属性 - 候选人的类型不匹配

Swift数组初始化程序语法类型不匹配

如何使用与 NewtonSoft (JSON.Net) 组件中的 JSON 匹配的 Swift 类从/向 JSON 读取/写入对象数组?

Json 数据和我创建的类之间不匹配