Swift NSUserDefaults 第一次为零

Swift NSUserDefaults first time nil

嗨,我的应用程序在我第一次 运行 时崩溃了。这是我的代码:

 let State = save.stringForKey("StateSave")
 let City = save.stringForKey("CitySave")
 let Vehicle = save.stringForKey("ModelNumberSave")
 let ExtensionPeriod = save.stringForKey("ExtensionPeriodChoosed")
 let Location = "Location"


 if ExtensionPeriod == nil {
      let name = ""
      var FieldChoosed: Void = save.setObject(name, forKey: "ExtensionPeriodChoosed")
      save.synchronize()

 }

 save.synchronize()
 var DetailNames = ["\(State!)","\(City!)","\(Location)","\(Vehicle!)","\(ExtensionPeriod!)"]

我在这一行得到了 nil

var DetailNames = ["(State!)","(City!)","(Location)","(Vehicle!)","(ExtensionPeriod!)"]

其实ExtensionPeriod就是nil。但是我不明白为什么...ExtensionPeriodnil,但是用我写的代码,ExtensionPeriod会像“”所以它不是nil。请帮助我。

stringForKey returns nil 当还没有保存值时。

您需要给您的值一个默认值。最简单的方法是使用 ?? 运算符,将 nil 替换为另一个值:

let State = save.stringForKey("StateSave") ?? "-"

一些一般性建议:您需要停止使用 !。通常当某些东西 returns nil 时,这是有充分理由的——它可能是 nil。当您使用 ! 解包时,您的程序将崩溃(关于原因的有用信息不多)。同样,如果您将值与 nil.

进行比较,这通常是一个不好的迹象

相反,请查看 一些备选方案的可选处理技术。

Airspeed Velocity 有一个很好的解决方案,可以正确地完成你想做的事情,但他没有真正解释为什么你所做的不起作用,所以我将解决这个问题的那个方面。

if ExtensionPeriod == nil {
    let name = ""
    var FieldChoosed: Void = save.setObject(name, forKey: "ExtensionPeriodChoosed")
    save.synchronize()
}

该代码块未设置ExtensionPeriod,因此ExtensionPeriod 仍为nil。它所做的只是将 NSUserDefaults 中的键“ExtensionPeriodChoosed”的值设置为不再为 nil。然而,局部变量 ExtensionPeriod 仍然为 nil。 ExtensionPeriod 不只是神奇地指向存储在 NSUserDefaults 中的变量,这样当您更新 NSUserDefaults 时,它会自动更新该变量。相反,它会在创建变量时复制变量。

这里有一些示例代码可以演示这一点:

    NSUserDefaults.standardUserDefaults().setValue("string", forKey: "s")
    NSUserDefaults.standardUserDefaults().synchronize()
    var s = NSUserDefaults.standardUserDefaults().valueForKey("s")
    
    NSUserDefaults.standardUserDefaults().setValue("string2", forKey: "s")
    NSUserDefaults.standardUserDefaults().synchronize()
    var y = NSUserDefaults.standardUserDefaults().valueForKey("s")
    
    println(s)
    println(y)

输出:

"string"

"string2"

为了让您的代码正常工作,如果您要保持相同的结构(尽管您确实不应该这样做),则需要将 ExtensionPeriod 更改为 var,然后在您的 if 块中,同步保存后,您必须将 ExtensionPeriod 重新分配给 save.valueForKey("ExtensionPeriodChoosed").

确保应用默认设置的一种方法是使用 NSUserDefaultregisterDefaults(_: [NSObject : AnyObject]) 函数。在 Objective-C 中,我经常放入 + (void)initialize class 方法,但重写应用程序委托的 init() 应该也能正常工作。