Swift如何解码键为递增编号的嵌套字典结构JSON数据
解决方案
方案1:直接修改模型适配字典结构(实现成本最低)
仅需修改DataStructure中elements的属性类型,即可直接完成解码:
public class DataStructure: Codable { let id: Int64? // 把原来的[ElementStructure]? 改成 [String: ElementStructure]? let elements: [String: ElementStructure]? init(id: Int64?, elements: [String: ElementStructure]?) { self.id = id self.elements = elements } }
解码完成后如果需要获取元素数组,直接提取字典的values即可:
let elementArray = Array(dataInstance.data.elements?.values ?? [])
方案2:自定义解码逻辑,保持原有数组类型(无需修改后续业务代码)
如果不想改动原有调用elements数组的业务逻辑,可以通过重写DataStructure的解码初始化方法,自动把字典转换为数组存储:
public class DataStructure: Codable { let id: Int64? let elements: [ElementStructure]? enum CodingKeys: String, CodingKey { case id, elements } public required init(from decoder: Decoder) throws { let container = try decoder.container(keyedBy: CodingKeys.self) id = try container.decodeIfPresent(Int64.self, forKey: .id) // 先解码为字典结构,再提取values转为数组 let elementsDict = try container.decodeIfPresent([String: ElementStructure].self, forKey: .elements) elements = elementsDict.map { Array($0.values) } } init(id: Int64?, elements: [ElementStructure]?) { self.id = id self.elements = elements } }
该方案无需修改原有解码函数、也无需改动后续使用elements数组的逻辑。
如需保留E01/E02这类键值
如果业务需要用到每个元素对应的前缀键,可以给ElementStructure新增属性存储键:
public class ElementStructure: Codable { let key: String? // 新增字段存储E01/E02这类键 let title: String? let items: [String]? let details: DetailStructure? init(key: String?, title: String?, items: [String]?, details: DetailStructure?) { self.key = key self.title = title self.items = items self.details = details } }
对应修改DataStructure的解码逻辑,把字典的键赋值给每个元素:
public required init(from decoder: Decoder) throws { let container = try decoder.container(keyedBy: CodingKeys.self) id = try container.decodeIfPresent(Int64.self, forKey: .id) let elementsDict = try container.decodeIfPresent([String: ElementStructure].self, forKey: .elements) // 遍历字典把键存入元素 elements = elementsDict?.map { key, value in ElementStructure( key: key, title: value.title, items: value.items, details: value.details ) } }
内容的提问来源于stack exchange,提问作者latenightsike
相关产品推荐
相关产品推荐

