什么是NSUserDefaults的限制?

在iPhone中永久存储数据通常使用Core Data或sqlite3来完成。 大多数人更喜欢将NSUserDefaults作为应用程序首选项的存储,而不是将其用作普通数据库(如sqlite)。

我发现大量的数据可以存储在NSUserDefaults中,使用起来非常简单,而且速度很快。 那么为什么不把它当作永久存储呢? NSUserDefaults作为数据库的局限性是什么?

更新:
我经常使用三种不同的方法将数据保存到磁盘。

  • 核心数据
  • 将对象序列化为plists
  • NSUserDefaults的

我不再使用FMDB(或直接使用sqlite)。 每种方法的主要优点和缺点是什么?

我遇到的NSUserDefaults的一些优点:

  • sorting,分组等可以很容易地使用NSPredicate来完成。
  • NSUserDefaults是线程安全的。
  • 它需要一行来获取并保存数据到NSUserDefaults。

NSUserDefaults提供了一个简单的学习曲线和线程安全的实现。

否则,我发现Core Data在各方面都很出色。 特别是关于configuration默认值和迁移例程。

编辑:事实certificate,NSUserDefaults“线程安全性”似乎来自主线程上运行的操作。 这在我的一个应用程序中导致严重的跳帧。 我最终取出了NSUserDefaults,并用一个线程安全的NSMutableDictionaryreplace它,将其序列化为一个文件。

Sqlite3对于保持大型数据库和访问数据库元素更有用。 您可以对Sqlite3数据库的项目进行sorting,您可以在Sqlite3 dtabase中快速search项目。 Sqlite3数据库有很多NSUserDefaults没有的权限!


NSUserDefaults vs Sqlite3

NSUserDefaults用于用户首选项,通常是像NSString或NSNumber这样的基本对象。 序列化属性列表中的对象集合或核心数据的Sqlite都是用于存储用户数据(如所创build的模型对象)的有效选项。

你不会看到一个速度的差异,但最好还是select正确的机制。 如果只是首选项,然后使用NSUserDefaults,否则我会序列化您的对象到plist。 如果你是Cocoa的新手,我会首先避免使用Core Data,甚至是Sqlite,给自己一个首先学习基础知识的机会。


NSUserDefaults或Sqlite

当你想存储大量的数据与一些关系,去Sqlite,如果你想存储较less的价值去NSUserDefaults。 Sqlite占用一些内存,所以使用它只有你真的需要保存复杂的数据。


使用NSUserDefaults来保存大量的游戏数据

通常NSUserDefaults用于保存游戏设置。 为了保存游戏数据,通常最好使用SQLite,或者你可以创build一个对象的NSDictionary并保存到磁盘,在这里可以帮助你:

  1. http://www.cocos2d-iphone.org/forum/topic/9308
  2. http://www.cocos2d-iphone.org/forum/topic/9210

对于我目前正在进行的一个项目,我需要build立一个大型的数据库(大约有400.000条logging)。 如果使用NSUserDefaults,则必须添加可能需要几分钟的logging(取决于设备以及如何导入数据)。 如果您使用CoreData,只需将预先构build的数据库复制到应用程序的文档目录中即可使用。

这就是为什么我依靠CoreData。

CoreData的一个优点是你的对象将是一个带有属性的NSManagedObject。 这意味着当您获取或设置值时,您将拥有自动完成function来帮助您使用属性名称。 它也使更多的可读代码。

与NSUserDefaults同时,您必须始终使用键值访问器,使用string作为键。

即:

myGlobalSettingsObject.lastLoginTime = @(now);

[[NSUserDefaults standardUserDefaults] setValue:@(now) forKey:@"lastLoginTime"];

如果你不小心在某个地方设置了键,就会发生错字? 编译器不会警告你。 如果某人在某处放置了错误的types呢? 编译器不会警告你。

例如:

[[NSUserDefaults standardUserDefaults] setValue:@"now" forKey:@"lastLoginTiem"]; ^ ^ ^^^^

…在build造时不会造成警告或错误…危险!

使用NSManagedObject的其他好处是可以validation; 它可以确保非空值; 它可以有自定义的getter和setter方法,可以用来做一些很酷的事情; 它可以处理自动迁移,如果你改变一些关于如何存储值的东西; 并且其数据模型成为您的存储库的一部分,因此您可以轻松地跟踪其更改的历史logging。

同时,NSUserDefaults是快速和肮脏的,很适合基本的小应用程序,但它是非常原始的。 很适合一个小应用程序,但是如果你有一个巨大的应用程序,与使用核心数据相比,它将变得很难pipe理。

关于NSUserDefaults的唯一可能的事情是,如果你的应用程序需要删除它的CoreData存储,或者你不想为实现线程安全的CoreData而烦恼,那么在这方面维护就会less一些。