如何在没有键的情况下快速编码解码 JSON 中的数组 [关闭]

问题描述 投票:0回答:1

我正在使用返回这个非常可怕的 JSON 的 API:

{
    "error":false,
    "country":"USA",
    "country_id":"881",
    "operator":"Operatp",
    "operator_id":"2053",
    "logo":"https://logo-2053-1.png",
    "destination_currency":"USD",
    "product_list":[
      "10",
      "20",
      "50",
      "100",
      "200",
      "500"
    ],
    "product_options":[
      {
         "10 RUB":"\u0026dollar;1.00 USD"
      },
      {
         "20 RUB":"\u0026dollar;2.00 USD"
      },
      {
         "50 RUB":"\u0026dollar;5.00 USD"
      },
      {
         "100 RUB":"\u0026dollar;9.99 USD"
      },
      {
         "200 RUB":"\u0026dollar;19.98 USD"
      },
      {
         "500 RUB":"\u0026dollar;49.95 USD"
      }
    ]
}

我正在尝试使用 JSONDecoder 解码嵌套数组,但它没有单个键,我真的不知道从哪里开始。你有什么想法吗?

let test = try JSONDecoder().decode(Options.self, from: data!)
for options in test.options {
    print(options)
}
struct Options : Decodable {
    let options : [String]
}

我得到的错误

_JSONKey(stringValue: "Index 0", intValue: 0)], debugDescription: “预期解码 String 但发现了一本字典。”, 底层错误:无))

json swift codable
1个回答
1
投票

免责声明-在我写下这个答案的那一刻,问题就不同了。 作者可能修改过

所以你的回答是这样的:

{
    "options": [
        { 
            "A" = "A"
        },
        { 
            "B" = "B"
        },
        { 
            "C" = "C"
        }
    ]
}

JSON 解码器所做的就是尝试将响应映射到预布局的 Codable/Decodable 结构。你越具体,验证就越具体。由于 Swift 是类型安全的,因此您必须注意数据类型。

所以在你的情况下你的回应看起来像:

1 - 带有一个键“选项”的字典,它是一组东西

struct Options : Codable {
    let options : [Data]
}

2 - “选项”是一组键值字典(或对象)

typealias ElementType = [String: Data]
struct Options : Codable {
    let options : [ElementType]
}

3 - 每个字典都有字符串键和字符串值

typealias ElementType = [String: String]
struct Options : Codable {
    let options : [ElementType]
}

4-(更进一步)如果您已经知道您将获得的键名(A、B、C) 你可以像这样创建一个带有可选参数的对象。 所以每个对象都将填充正确的键值对,剩下的

nil

struct MyObject : Codable {
    let A : String?
    let B : String?
    let C : String?
}
struct Options : Codable {
    let options : [MyObject]
}

5-(奖励)通常用于快速样式指南,变量名保持小写,所以如果你想映射你的自定义变量名,你可以这样做

struct MyObject : Codable {
    let customName1 : String?
    let customName2 : String?
    let C : String?
    
    enum CodingKeys: String, CodingKey {
        case customName1 = "A" // put whatever in 'A' inside 'customName1'
        case customName2 = "B"
        
        // default
        case C
    }
}
struct Options : Codable {
    let options : [MyObject]
}

祝你好运!

© www.soinside.com 2019 - 2024. All rights reserved.