Swift中Encodable类如何为不同日期属性设置不同编码格式?
为Encodable类的不同Date属性设置不同编码格式
问题描述
我有一个遵循Encodable协议的类,包含两个Date类型的属性。编码为JSON字符串时,希望两个日期使用不同格式:
date1采用ISO8601格式(如"2022-10-24T22:03:43Z")date2采用时间戳格式(如688342014.16646099)
尝试示例代码后未能实现,请问该如何为不同属性设置不同日期格式?是否需要重写JSONEncoder.encode()方法?
示例代码:
func getString() -> String? { let encoder = JSONEncoder() encoder.outputFormatting = .prettyPrinted encoder.dateEncodingStrategy = .iso8601 guard let data = try? encoder.encode(TwoDates()) else { return nil } guard let dataString = String(data: data, encoding: .utf8) else { return nil } return dataString } class TwoDates: Encodable { public var date1 = Date() public var date2 = Date() public func encode(to encoder: Encoder) throws { var container = encoder.container(keyedBy: CodingKeys.self) try? container.encode(date1, forKey: .date1) try? container.encode(date1, forKey: .date2) // 此处错误重复编码date1 } enum CodingKeys: String, CodingKey { case date1 = "date1" case date2 = "date2" } }
解决方案
不需要重写JSONEncoder.encode()方法,只需在自定义的encode(to:)方法中分别处理两个Date属性的编码逻辑即可:
- 对于
date1,直接利用encoder已设置的.iso8601编码策略完成编码。 - 对于
date2,将其转换为时间戳(通过Date的timeIntervalSince1970属性获取带小数的秒数),再编码这个数值类型即可输出时间戳格式。 - 替换原代码中错误的重复编码逻辑,同时改用
try替代try?,避免忽略编码错误,方便调试。
修改后的完整代码:
func getString() -> String? { let encoder = JSONEncoder() encoder.outputFormatting = .prettyPrinted encoder.dateEncodingStrategy = .iso8601 do { let data = try encoder.encode(TwoDates()) return String(data: data, encoding: .utf8) } catch { print("编码失败:\(error)") return nil } } class TwoDates: Encodable { public var date1 = Date() public var date2 = Date() public func encode(to encoder: Encoder) throws { var container = encoder.container(keyedBy: CodingKeys.self) // 按ISO8601格式编码date1 try container.encode(date1, forKey: .date1) // 将date2转为时间戳后编码 try container.encode(date2.timeIntervalSince1970, forKey: .date2) } enum CodingKeys: String, CodingKey { case date1 = "date1" case date2 = "date2" } }
代码说明
date1的编码依赖JSONEncoder设置的dateEncodingStrategy = .iso8601,会自动生成符合ISO8601标准的字符串。date2通过timeIntervalSince1970获取从1970年1月1日00:00:00 UTC到当前日期的秒数(带小数精度),编码该Double值后,JSON中会直接显示为时间戳格式。- 使用
do-catch捕获错误,能及时定位编码过程中出现的问题,提升调试效率。
内容的提问来源于stack exchange,提问作者Bartosz Jarosz
相关产品推荐
相关产品推荐

