swift - NSKeyedArchiver 无法归档对象
问题描述
我有一个从磁盘读取的 JSON 文件
这是文件的结构:
[
{
"name": "3X",
"priority": 33
},
{
"name": "4X",
"priority": 32
}
]
我正在将其解码为一个名为Test
class TestClass: NSObject, Codable {
enum CodingKeys: String, CodingKey {
case name, priority
}
let name:String
let priority:Int
var optional:String? = nil
var problem:String = "eli"
init(name:String, priority:Int, optional:String? = nil, problem:String) {
self.name = name
self.priority = priority
self.optional = optional
self.problem = problem
super.init()
}
}
这是我用来解码文件的代码
if let path = Bundle.main.path(forResource: "test", ofType: "json") {
do {
let jsonData = try Data(contentsOf: URL(fileURLWithPath: path), options: .mappedIfSafe)
let testObjects = try JSONDecoder().decode([TestClass].self, from: jsonData)
let data = try! NSKeyedArchiver.archivedData(withRootObject: testObjects, requiringSecureCoding: false)
UserDefaults.standard.set(data, forKey: "test_objects")
} catch {
// error in parsing json
}
}
解码后,我尝试将数组保存到磁盘中,我将其转换为 NSData 以进行保存,但是NSKeyedArchiver.archivedData
失败并出现以下错误:
{NSDebugDescription=Caught exception during archival: -[BugTesting.TestClass encodeWithCoder:]: unrecognized selector sent to instance 0x600002119ac0
对我来说,这看起来很奇怪,因为我遵守Codable
.
任何帮助,将不胜感激。
解决方案
如果您想对此进行编码,我可能会建议PropertyListEncoder
. 那么你就不需要引入与以下相关的NSObject
(也不是NSCoding
/ NSSecureCoding
cruft)NSKeyedArchiver
:
class TestClass: Codable {
enum CodingKeys: String, CodingKey {
case name, priority
}
let name: String
let priority: Int
var optional: String?
var problem: String?
init(name: String, priority: Int, optional: String? = nil, problem: String? = nil) {
self.name = name
self.priority = priority
self.optional = optional
self.problem = problem
}
}
然后编码:
let data = try PropertyListEncoder().encode(test)
并解码:
let test2 = try PropertyListDecoder().decode(TestClass.self, from: data)
我不确定你为什么不编码optional
或problem
. 我可能也倾向于对这些进行编码,除非出于某种原因您想在编码/解码过程中丢失该数据。如果您希望对所有属性进行编码,则可以消除CodingKeys
:
class TestClass: Codable {
let name: String
let priority: Int
var optional: String?
var problem: String?
init(name: String, priority: Int, optional: String? = nil, problem: String? = nil) {
self.name = name
self.priority = priority
self.optional = optional
self.problem = problem
}
}
推荐阅读
- react-native - 不变违规:仅反应预期的单个元素(将 Modal 可见从 false 更改为 true 时)
- spring-boot - 如何在 thymeleaf 中为输入和人类可读的文本输出使用不同的日期/时间格式
- csv - 从 tsv 文件加载关系在 neo4j 上不起作用
- asp.net-core - Specflow 测试用例死锁
- elasticsearch - Elasticsearch:“一个索引有很多分片”与“很多索引每个索引一个分片”
- spring-boot - 如何使用 Spring Boot 和 Kotlin 启动 Web 应用程序
- r - 如何在图形上用直线分割多边形?
- javascript - 如何将行号存储在数组中?
- apache-spark - 用 spark Scala 替换campaign_id 列的缺失值
- tableau-api - 想要使用 excel vba 从画面仪表板单击下载按钮