[我们有一个Swift类,该类继承自NSObject并实现NSCoding。我们需要在磁盘上的归档文件中的代码和中更改类的名称。幸运的是,我们不需要保留数据。清除缓存的文件并返回默认数据就可以了。问题在于检测何时失败并进行适当处理。
好吧,首先以这种方式写出数据(忽略用力展开等引起的自由,只是为了使问题保持简洁):]
let someObject: [Int: MyClass] = ... let data = NSKeyedArchiver.archivedData(withRootObject: someObject) try! data.write(to: someUrl, options: .atomic)
这很好。我们现有的解码方法是这样的(再次,我们的代码在实践中更安全):
let someObject = NSKeyedUnarchiver.unarchiveObject(withFile: someUrl.path)! as! [Int: MyClass]
现在,当我们重命名我们的类时,我们将不得不处理无法解码的情况。使用NSKeyedUnarchiver,可以设置一个委托,如果解码失败,该委托将具有一个称为的方法。在更改它之前,我想重新编写我们现有的解码器,以确保它可以在进行任何更改之前按原样解码。不幸的是,它不能。这是我们得到的:
let fileData = fileManager.contents(atPath: fileUrl.path)! let unarchiver = NSKeyedUnarchiver(forReadingWith: fileData) guard let myObject = try! unarchiver.decodeTopLevelObject() as? [Int: MyClass] else { return [Int: MyClass]() }
现在,我没想到会有任何问题。但是,对
decodetopLevelObject()
的调用每次都会失败,只是返回nil
(绝对不是问题所在的强制类型转换)。我不知道为什么。实际上没有相关文档。有一个类似的调用,它是decodeObject()
,但是也没有明显的原因而失败。我尝试设置委托并实现该方法,但从未调用过。
我们要去哪里错了?
[我们有一个Swift类,该类继承自NSObject并实现NSCoding。我们需要在代码中和磁盘上的存档中更改类的名称。幸运的是,我们不需要保留数据。...
尝试将decodeObject(forKey:)
与NSKeyedArchiveRootObjectKey
或类似的API一起使用。