Swift中如何解析未在CodingKeys定义的colorX格式JSON字段
解决方法
要将JSON中color1到color10(可能为空字符串)的字段解析到colors数组中,你可以通过访问解码器的完整键值容器,结合动态CodingKey来实现。以下是具体的代码实现:
完整代码实现
struct Cat: Decodable { let name: String let colors: [String] private enum CodingKeys: String, CodingKey { case name = "jsonName" } init(from decoder: Decoder) throws { // 解析固定的name字段 let container = try decoder.container(keyedBy: CodingKeys.self) name = try container.decode(String.self, forKey: .name) // 获取JSON的完整键值容器,支持访问所有字段 let fullContainer = try decoder.container(keyedBy: DynamicKey.self) var tempColors: [String] = [] // 循环处理color1到color10 for index in 1...10 { let colorKey = DynamicKey(stringValue: "color\(index)")! // 尝试解析字段:不存在或为空字符串则跳过 if let colorValue = try fullContainer.decodeIfPresent(String.self, forKey: colorKey), !colorValue.isEmpty { tempColors.append(colorValue) } } colors = tempColors } } // 自定义动态CodingKey,匹配任意字符串类型的键 private struct DynamicKey: CodingKey { let stringValue: String init?(stringValue: String) { self.stringValue = stringValue } let intValue: Int? init?(intValue: Int) { self.intValue = intValue self.stringValue = "\(intValue)" } }
关键逻辑说明
- DynamicKey结构体:实现
CodingKey协议,允许我们使用任意字符串作为键来访问JSON字段,完美适配color1、color2这类动态命名的字段。 - 完整容器访问:通过
decoder.container(keyedBy: DynamicKey.self)获取整个JSON的键值容器,突破了CodingKeys仅能访问指定字段的限制。 - 循环解析与过滤:遍历1到10的索引,构造对应的
colorX键,用decodeIfPresent安全解析——如果字段不存在,或者解析出空字符串,直接跳过;有效内容则加入数组。
灵活扩展方案(可选)
如果JSON中的color字段数量不固定(可能多于或少于10个),可以通过筛选所有以color开头的键来实现,同时注意按数字排序避免顺序混乱:
// 替换循环部分的代码 let allColorKeys = fullContainer.allKeys.filter { $0.stringValue.hasPrefix("color") } // 按color后的数字排序,确保color2在color10前面 let sortedKeys = allColorKeys.sorted { guard let num1 = Int($0.stringValue.replacingOccurrences(of: "color", with: "")), let num2 = Int($1.stringValue.replacingOccurrences(of: "color", with: "")) else { return false } return num1 < num2 } for key in sortedKeys { if let colorValue = try fullContainer.decodeIfPresent(String.self, forKey: key), !colorValue.isEmpty { tempColors.append(colorValue) } }
内容的提问来源于stack exchange,提问作者alex17
相关产品推荐
相关产品推荐

