NSUserDefaults官方
它底层是一个xml格式的plist文件保存在应用程序的沙箱中。
文档中给了开发者提供了两个例子:
- 可以存储一些应用中常用的测量单位
- 存储用户喜欢的多媒体播放速度
在应用程序运行期间数据库中的数据可以多线程读取这个没有问题,但是设置值的时候,NSUserDefaults会在使用线程中同步的修改这个值,但是其实真正持久化到数据库的时候是异步的。同时NSUserDefaults也提供了方法用于强制将当前值写入持久存储。
同时需要注意的是不要在应用程序中自己打开那些存储文件。存储默认对象 对于一些基础的默认数据类型,NSUserDefaults提供了一些便捷方法来设置他们。包括:
Don’t try to access the preferences subsystem directly. Modifying preference property list files may result in loss of changes, delay of reflecting changes, and app crashes. To configure preferences, use the defaults command-line utility in macOS instead.
- float
- double
- integer
- boolean
- url
- NSData
- NSString
- NSNumber
- NSDate
- NSArray
- NSDictionary
其中集合中包含的对象也必须是他们中的一员,不行的话就只能归档了。
- NSArgumentDomain
- Application
- NSGlobalDomain
- Languages
- NSRegistrationDomain
NSArgumentDomain -> Application -> NSGlobalDomain -> Languages -> NSRegistrationDomain
关于这部分内容可以参考该文:
NSUserDefaults - 熟悉与陌生
持久化文件引用 其实主要是通过在文件系统生成文件bookmark的做法来防止存放文件URL之后,文件路径被修改。
关于iOS中的URL可以参考这篇文章:
iOS-Foundation NSURL
响应偏好改变 我们可以使用kvo来监听某个默认值的变化。其中key为你存储在用户偏好中的值。
[[NSUserDefaultsController sharedUserDefaultsController] addObserver:self
forKeyPath:@"values.key"
options:NSKeyValueObservingOptionNew
context:NULL];
简单点可以写为
[[NSUserDefaults standardUserDefaults] addObserver:self
forKeyPath:@"key"
options:NSKeyValueObservingOptionNew
context:NULL];
关于沙盒的考虑 一个基于沙盒管理的App一般情况下是不能修改其他沙盒下的App的,有两种情况例外:
- macOS 或 iOS App的extensions
- macOS中App包含在一个group中
- 开启AppGroup
文章图片
image.png - 初始化针对该group的用户偏好文件
NSUserDefaults *shareUserDefault = [[NSUserDefaults alloc] initWithSuiteName:@"group.xxxx"];
if (![shareUserDefault boolForKey:@"FirstVoiceManagerProfile"]) {
[shareUserDefault setBool:YES forKey:OPEN_KEY];
[shareUserDefault setBool:YES forKey:@"FirstVoiceManagerProfile"];
}
- 读取共享用户偏好
//获取共享域的偏好设置
NSUserDefaults *shareUserDefault = [[NSUserDefaults alloc] initWithSuiteName:@"group.xxxx"];
//解析推送自定义参数userInfo
NSDictionary *userInfo = [self dictionaryWithUserInfo:self.bestAttemptContent.userInfo];
BOOL canSound = [shareUserDefault boolForKey:OPEN_KEY];
NSString *voiceString = nil;
//
if (canSound && userInfo) {
voiceString = [NSString stringWithFormat:@"收款%@元!", userInfo[@"money"]];
}
线程安全 【二、NSUserDefaults】NSUserDefaults是线程安全的。