如何根据给定JSON编写适配JSONDecoder的结构体及CodingKeys作用
Swift JSON解析:Codable建模与CodingKeys用法说明
根据JSON样例编写Codable结构体的标准流程
- 逐层对齐JSON结构:JSON最外层为对象时对应自定义结构体,为数组时对应
[元素类型]数组;字段值类型严格匹配:字符串对应String、整数对应Int、浮点数对应Double、布尔值对应Bool、可能返回null的字段必须声明为可选类型(如String?) - 所有参与解析的自定义类型按需遵守协议:仅做JSON转模型时遵守
Decodable即可,需要双向转码(模型转JSON)时遵守Codable - 嵌套JSON对象直接在对应结构体内部定义子结构体,层级和JSON保持完全一致即可
举个实际示例,给定如下JSON返回:
{ "user_id": 1024, "user_name": "Alex", "is_vip": true, "profile": { "avatar": "avatar_path.png", "register_ts": 1690000000 } }
基础版结构体可直接按如下方式编写:
struct User: Decodable { let userId: Int let userName: String let isVip: Bool let profile: Profile struct Profile: Decodable { let avatar: String let registerTs: Int } }
CodingKeys枚举的核心作用
你在代码里看到的CodingKeys是Codable体系里的自定义映射枚举,必须遵守CodingKey协议,核心作用有三个:
- 解决命名规范差异:Swift开发习惯用驼峰命名(如
userId),但绝大多数后端接口返回的JSON用蛇形命名(如user_id),通过CodingKeys可以给每个属性绑定对应的JSON字段名,不需要强制让Swift属性名和JSON字段名完全一致 - 控制参与解析的字段范围:结构体中如果有仅本地业务使用、不需要从JSON解析的属性,只要不把它列在CodingKeys的case列表中,JSONDecoder解析时会自动忽略该字段,不会抛出字段不匹配的错误
- 支撑自定义解码逻辑:如果需要对字段做类型转换、默认值填充、多字段合并等自定义操作,重写
init(from decoder: Decoder)方法时,需要通过CodingKeys从解码容器中取出对应字段的值
给上面的User结构体加上CodingKeys后的完整可运行代码如下:
struct User: Decodable { let userId: Int let userName: String let isVip: Bool let profile: Profile // 本地业务用属性,不参与JSON解析 var isFollowed: Bool = false enum CodingKeys: String, CodingKey { case userId = "user_id" case userName = "user_name" case isVip = "is_vip" case profile // 未列出isFollowed,解析时自动跳过 } struct Profile: Decodable { let avatar: String let registerTs: Int enum CodingKeys: String, CodingKey { case avatar case registerTs = "register_ts" } } }
实用技巧:如果你的接口返回全是标准蛇形命名,不需要给每个字段手写CodingKeys映射,只要给JSONDecoder设置对应策略即可自动完成驼峰转蛇形的匹配:
let decoder = JSONDecoder() decoder.keyDecodingStrategy = .convertFromSnakeCase
你自己写的结构体如果解析报错,可以对照三个规则排查:
- 非可选属性的类型必须和JSON返回的字段类型完全一致,类型不匹配会直接抛出解码失败
- 结构体嵌套层级必须和JSON结构完全对应,层级错位会导致找不到字段
- 可能缺失、返回null的字段必须声明为可选类型,否则遇到空值会解码失败
内容的提问来源于stack exchange,提问作者Rakha Fatih
相关产品推荐
相关产品推荐

