Swift3:[String:AnyObject]使用NSCoding协议与NSUserDefaults一起保存

时间:2016-09-29 16:18:47

标签: swift nsuserdefaults nscoding

我有我的自定义类:

private class PendingRequest : NSObject, NSCoding
{
    var route : String!
    var params: [String: AnyObject]!

    init(route: String, params: [String: AnyObject])
    {
        self.route = route
        self.params = params
    }
    required init(coder aDecoder: NSCoder)
    {
        self.route = aDecoder.decodeObject(forKey: "route") as! String
        self.params = aDecoder.decodeObject(forKey: "params") as! [String: AnyObject]
    }

    public func encode(with coder: NSCoder)
    {
        coder.encode(route, forKey: "route")
        coder.encode(params, forKey: "params")
    }
}

以下是我保存PendingRequest

列表的方法
private static func savePendingRequests(requestsToSend: [PendingRequest])
{
    let data = NSKeyedArchiver.archivedData(withRootObject: requestsToSend!)
    UserDefaults.standard.set(data, forKey: self.requestsToSendDefaultsString)
}

以下是我尝试检索它的方法:

let data = UserDefaults.standard.data(forKey: requestsToSendDefaultsString)
let requests = NSKeyedUnarchiver.unarchiveObject(with: data!) as! [PendingRequest]
return requests

但是我的代码在检索我的数据时崩溃了...保存工作正常,但没有检索......任何想法?

编辑:这是我的Crashlytics错误:

*** -[NSKeyedUnarchiver decodeObjectForKey:]: cannot decode object of class (_TtCC6Versus9VersusAPIP33_8D2B8AA415FDC4F8DFAF29D7ECE33C1F14PendingRequest) for key (NS.objects); the class may be defined in source code or a library that is not linked

SOLUTION:

我的班级PendingRequestfileprivate,因此NSKeyedUnarchiver无法访问,因此崩溃......感谢您的帮助。

1 个答案:

答案 0 :(得分:0)

很少有事情不正确

您忘记在初始化程序中调用super.init()

init(route: String, params: [String: AnyObject])
{
    self.route = route
    self.params = params
    super.init()
}
required init(coder aDecoder: NSCoder)
{
    self.route = aDecoder.decodeObject(forKey: "route") as? String
    self.params = aDecoder.decodeObject(forKey: "params") as? [String: AnyObject]


    // Check if route and params are what you expected here


    super.init()
}

你有一个静态的方法来调用" self",我不确定这是否有效,你仍然可以拥有静态密钥或全局密钥。 此外,您还要展开非可选值" requestsToSend"。 我想这会解决它。

private static func savePendingRequests(requestsToSend:[PendingRequest])
{
     let data = NSKeyedArchiver.archivedData(withRootObject: requestsToSend)
     UserDefaults.standard.set(data, forKey: "AStaticKey")
}

然后检索应该工作。 (我添加了一些安全检查)

guard let data = UserDefaults.standard.data(forKey: "AStaticKey"), 
      let requests = NSKeyedUnarchiver.unarchiveObject(with: data) as? [PendingRequest] else {
         return [PendingRequest]()
      }
return requests