【问题标题】:How to decode a nested JSON struct with dynamic variable from API call如何从 API 调用中解码带有动态变量的嵌套 JSON 结构
【发布时间】:2019-05-11 18:53:35
【问题描述】:

调用此特定 API 时,其中一个变量会根据结果发生变化。

例子:

{
    "map": {
        "1945206": {
            "installBaseNUMB": 0,
            "serialNumber": "KB1",
            ...
        }
    }
}

1945206 将更改为另一个数字,我不知道如何正确解码。

我的 Codable 结构如下:

struct Map: Codable {
    let the1945206: The1945206?

    enum CodingKeys: String, CodingKey {
        case the1945206 = "1945206"
    }
}

struct The1945206: Codable {
    let installBaseNUMB: Int?
    let serialNumber, woStatus: String?
    let workOrderNumber: Int?
    let woNotes: [String]?
    let woParts: [WoPart]?
}

如果 1945206 更改为另一个值,它将中断并且不会显示任何结果。如何在解码数据时使用动态变量?

【问题讨论】:

标签: json swift codable


【解决方案1】:

试试这个:

struct Install: Decodable {
    let installBaseNUMB: Int, serialNumber: String
}

let installData = try? JSONDecoder().decode([String:[String:Install]].self, from: jsonData2!)
let install = installData?.values.first?.values.first

【讨论】:

    【解决方案2】:

    你可以试试

    struct Root : Codable {
       let map: [String:The1945206]
    }
    

    let res = try? JSONDecoder().decode(Root.self,from:data)
    print(res?.map.values)
    

    {
        "map": {
            "1945204": {
                "installBaseNUMB": 0,
                "serialNumber": "KB1",
                ...
            },
            "1945205": {
                "installBaseNUMB": 0,
                "serialNumber": "KB1",
                ...
            },
            "1945206": {
                "installBaseNUMB": 0,
                "serialNumber": "KB1",
                ...
            }
        }
    }
    

    【讨论】:

      【解决方案3】:

      我建议设置与The1945206 不同的名称,因为它的可读性较差。我将改用MapElement。如果您知道 map 将只有一个元素,并且您不想检查与此值关联的键,则可以使用计算属性 var value:MapElement? 来获取它。它返回一个可选的,因为let map:[String:MapElement] 字典可以为空。

      let json = """
      {
          "map": {
              "1945206": {
                  "installBaseNUMB": 0,
                  "serialNumber": "KB1"
              }
          }
      }
      """.data(using: .utf8)!
      
      struct Container: Codable {
          let map:[String:MapElement]
      
          var value:MapElement? {
              return map.values.first
          }
      }
      
      struct MapElement: Codable {
          let installBaseNUMB: Int
          let serialNumber: String
      }
      
      let res = try? JSONDecoder().decode(Container.self,from:json)
      print(res?.value as Any)
      

      更新:

      如果您想使用多个MapElement,可以将var value:MapElement 更改为var values:[MapElement],如下所示:

      struct Container: Codable {
          let map:[String:MapElement]
      
          var values:[MapElement] {
              return map.values
          }
      }
      

      但请记住,您将数据存储为字典,因此无法保证元素的顺序。

      【讨论】:

        猜你喜欢
        • 1970-01-01
        • 2019-12-14
        • 2020-10-29
        • 2021-08-07
        • 1970-01-01
        • 1970-01-01
        • 2011-11-10
        • 1970-01-01
        • 1970-01-01
        相关资源
        最近更新 更多