Swift中Type 'Post'未遵循Decodable协议错误如何修复?
修复「Type 'Post' does not conform to protocol 'Decodable'」错误
错误根源在于Post结构体中的timestampValue属性:它既没有默认值,也未包含在CodingKeys枚举中,而Swift默认的Codable合成逻辑要求所有存储属性都必须参与解码(要么在JSON中有对应字段,要么提供默认值)。
以下是三种常用修复方案:
方案1:将timestampValue改为计算属性(推荐,若它基于已有属性生成)
如果timestampValue是通过timeshamp(注意代码中拼写错误,建议修正为timestamp)转换而来的字符串,直接改为计算属性即可脱离Codable的编码解码流程:
import Foundation struct PostsModel: Codable { let posts: [Post] } struct Post: Codable { let postID, timestamp, likesCount: Int // 修正拼写:timeshamp → timestamp let title, previewText: String // 计算属性,基于timestamp生成格式化字符串 var timestampValue: String { let date = Date(timeIntervalSince1970: TimeInterval(timestamp)) let formatter = DateFormatter() formatter.dateFormat = "yyyy-MM-dd HH:mm:ss" return formatter.string(from: date) } enum CodingKeys: String, CodingKey { case timestamp, title // 同步修正拼写 case postID = "postId" case previewText = "preview_text" case likesCount = "likes_count" } }
方案2:给timestampValue添加默认值(若它需存储但不依赖JSON数据)
如果timestampValue是需要保留的存储属性,但不需要从JSON中解码,给它设置默认值即可让Swift自动合成Codable实现:
import Foundation struct PostsModel: Codable { let posts: [Post] } struct Post: Codable { let postID, timeshamp, likesCount: Int let title, previewText: String // 添加默认值 var timestampValue: String = "" enum CodingKeys: String, CodingKey { case timeshamp, title case postID = "postId" case previewText = "preview_text" case likesCount = "likes_count" } }
方案3:手动实现Decodable协议(灵活控制解码流程)
如果需要自定义解码逻辑,比如在解码时直接初始化timestampValue,可以手动实现init(from:)方法:
import Foundation struct PostsModel: Codable { let posts: [Post] } struct Post: Codable { let postID, timeshamp, likesCount: Int let title, previewText: String var timestampValue: String enum CodingKeys: String, CodingKey { case timeshamp, title case postID = "postId" case previewText = "preview_text" case likesCount = "likes_count" } // 手动实现解码初始化 init(from decoder: Decoder) throws { let container = try decoder.container(keyedBy: CodingKeys.self) postID = try container.decode(Int.self, forKey: .postID) timeshamp = try container.decode(Int.self, forKey: .timeshamp) likesCount = try container.decode(Int.self, forKey: .likesCount) title = try container.decode(String.self, forKey: .title) previewText = try container.decode(String.self, forKey: .previewText) // 自定义timestampValue的初始化逻辑 timestampValue = String(timeshamp) } }
内容的提问来源于stack exchange,提问作者Никита Ященко
相关产品推荐
相关产品推荐

