NSUserDefaults Plist 创建在 Swift 中失败(但不是 Objective-C)

NSUserDefaults Plist Creation Fails in Swift (but not Objective-C)

我正在将我的一个项目从 Objective-C 转换为 Swift,并且 运行 遇到了一个奇怪的问题。考虑以下代码(在 -applicationDidFinishLaunching 中执行)...

Objective-C

一行乱码请见谅

[[NSUserDefaults standardUserDefaults] registerDefaults:
    [NSDictionary dictionaryWithContentsOfFile:[[NSBundle mainBundle] pathForResource:@"Defaults" ofType:@"plist"]]];

在我的 Objective-C 项目中,这按预期工作。如果我第一次 运行 我的应用程序并且不存在 plist,则在下一个 -synchronize 调用期间注册默认值并将其保存到新的 plist 中。如果 plist 已经存在但缺少一个值,它将从默认值中添加该值。有道理。

Swift

let defaults = NSUserDefaults.standardUserDefaults()
let plist = NSBundle.mainBundle().pathForResource("Defaults", ofType: "plist")
defaults.registerDefaults(NSDictionary(contentsOfFile: plist!) as! [NSObject : AnyObject])
defaults.synchronize()

在我的 Swift-exclusive 项目中,默认值被注册到内存中,但在调用 -synchronize 时它们永远不会写入磁盘。如果我记录一个值,我可以在执行上面的代码后立即测试并验证内存中是否存在默认值...

println(defaults.objectForKey("showUnread"))

但是这些值永远不会保存到 plist 中。即使我从界面更新我的绑定之一(所有这些都保存并完美保存),也不会为缺失值保存默认值。事实上,在我更新我的绑定之一之前,永远不会为我的应用程序创建 plist。

然而我的 Objective-C 项目,几乎是我的 Swift 项目的逐字翻译,运行完美。我一定是忽略了一些简单的事情,但我在 Google 和 Stack Overflow 上的搜索结果是空的。

故障排除步骤

  1. 创建了一个新的Swift项目,复制Defaults.plist到项目中并将上面的代码放在-applicationDidFinishLoading中。完全相同的结果。
  2. 已删除应用程序缓存和 plist,清空垃圾并重新启动。
  3. 我听说 cfprefsd 进程可以为已删除的文件维护一个 link,但它与使用相同包标识符的 Objective-C 代码一起工作正常。

registerDefaults 的调用从不保留任何数据(无论哪种语言)。这只是查找不存在的值时的后备。您认为应该将数据写入磁盘的期望不正确。

您对 synchronize 的调用没有执行任何操作,因为您尚未在 NSUserDefaults 中设置任何值。