stringForKey崩溃应用程序

用户名

我试图在NSUserDefaults中存储一个字符串,但是当我去检索它时,我的应用程序崩溃了。

我认为这只是第一次发生,因为从未在NSUserDefaults中为该键设置任何值,但是我尝试viewDidLoad()在第一次中添加一些代码来设置它,但这似乎无济于事。

这是我的代码:

override func viewDidLoad() {
    super.viewDidLoad()

    itemSelected = "Moss"
    NSUserDefaults.standardUserDefaults().setObject(itemSelected, forKey: "colourChosen")
}

override func viewWillAppear(animated: Bool) {
    itemSelected = NSUserDefaults.standardUserDefaults().stringForKey("colourChosen")!
}

func pickerView(pickerView: UIPickerView, didSelectRow row: Int, inComponent component: Int) {
    itemSelected = colours[row]
    NSUserDefaults.standardUserDefaults().setObject(itemSelected, forKey: "colourChosen")
}

该应用程序崩溃了 viewWillAppear()

有人有想法么?

安东尼奥

synchronize()设置对象后,您不会再调用

let userDefaults = NSUserDefaults.standardUserDefaults()
userDefaults.setObject(itemSelected, forKey: "colourChosen")
userDefaults.synchronize()
             ^^^^

否则,将不会立即保存任何更改。那可能是原因。

synchronize 每次更改用户默认值时都必须调用,并且要立即保留更改(系统会在特定时间间隔自动调用它)。

但是,在您的viewWillAppear实现中,我注意到您正在使用强制展开,除非您100%确保可选内容实际上包含非nil值,否则应始终避免这种情况。我会使用可选的绑定来保护这种展开:

if let colour = NSUserDefaults.standardUserDefaults().stringForKey("colourChosen") {
    itemSelected = color
}

更新

我注意到这itemSelected是您存储在用户默认值中的一个临时容器。您可以考虑将用户默认代码移动到计算出的属性中,以防止每次读取或修改该属性时都重复代码-类似于:

private var _itemSelected : String?

var itemSelected : String? {
    get {
        if _itemSelected == nil {
            _itemSelected = NSUserDefaults.standardUserDefaults().stringForKey("colourChosen")
        }
        return _itemSelected
    }
    set {
        let userDefaults = NSUserDefaults.standardUserDefaults()
        userDefaults.setObject(newValue, forKey: "colourChosen")
        userDefaults.synchronize()
    }
}

其中_itemSelected只是一个缓存值-或类似的实现,但没有缓存值:

var itemSelected : String? {
    get {
        return NSUserDefaults.standardUserDefaults().stringForKey("colourChosen")
    }
    set {
        let userDefaults = NSUserDefaults.standardUserDefaults()
        userDefaults.setObject(newValue, forKey: "colourChosen")
        userDefaults.synchronize()
    }
}

请注意,在两种情况下,属性类型都是可选字符串

本文收集自互联网,转载请注明来源。

如有侵权,请联系 [email protected] 删除。

编辑于
0

我来说两句

0 条评论
登录 后参与评论

相关文章