iOS 8在更新UserDefaults对象时冻结
我有一个存储到iOS 8在更新UserDefaults对象时冻结,ios,objective-c,nsuserdefaults,Ios,Objective C,Nsuserdefaults,我有一个存储到NSUserDefaults的对象队列。当需要向其添加对象时,我调用以下方法: + (void)addCodeToQueue:(Code *)code { // Note: userDefaults is a static, initialized variable NSDictionary *codeModel = [self generateCodeModelWith:code]; // Read array from UserDefaults, or crea
NSUserDefaults
的对象队列。当需要向其添加对象时,我调用以下方法:
+ (void)addCodeToQueue:(Code *)code {
// Note: userDefaults is a static, initialized variable
NSDictionary *codeModel = [self generateCodeModelWith:code];
// Read array from UserDefaults, or create one if nil
NSMutableArray *codeQueue = [userDefaults mutableArrayValueForKey:@"CodeQueue"] ? : [[NSMutableArray alloc] init];
// Add code model
[codeQueue addObject:codeModel];
// Add/replace array & sync
[userDefaults setObject:codeQueue forKey:@"CodeQueue"]; // App freezes here if uncommented
[userDefaults synchronize];
}
当我调用setObject:forKey
时,我的应用程序冻结。如果我在该行中添加一个断点,则继续运行,它就会工作。如果我不打破,它就会冻结
这是在我将Xcode更新到版本8并开始使用新的SDK之后发生的。
有什么提示吗?我在几个应用程序中也遇到过这个问题——通过mutableArrayValueForKey返回可变数组,你可能会陷入互斥锁。对于我的代码,我将其替换为:
- 将不可变数组获取为NSArray*arrSource=[defaults arrayworkey:strKey]李>
- 将数据复制到可变数组中: NSMUTABLEARRY*ARRMATABLE=[NSMUTABLEARRY arrayWithArray:arrSouce]李>
- 在arrMutable中设置我的值
- 将“修改过的”数组存储回默认值: [默认设置setObject:arrMutable forKey:strKey]李>
。。。至少对我来说,这解决了互斥锁问题。在我的实验之后,我找到了生成互斥锁所需的最少代码。 代码如下
NSMutableArray *videoArray = [[NSUserDefaults standardUserDefaults] mutableArrayValueForKey:VIDEOKEY];
[videoArray addObject:item];
[[NSUserDefaults standardUserDefaults] setObject:videoArray forKey:VIDEOKEY];
有三点需要注意:
[videoArray addObject:item]代码>,应用程序将崩溃
[[NSUserDefaults standardUserDefaults]setObject:videoArray forKey:VIDEOKEY]中代码>
[videoArray addObject:item]处设置断点代码>,互斥锁仍然存在。如果我在[[NSUserDefaults standardUserDefaults]setObject:videoArray-forKey:VIDEOKEY]进行设置代码>,互斥锁将不存在
[NSKeyValueSlowMutableArray addObject:]产生的
和[NSUserDefaults setObject:forKey:
顺便说一下,我的解决方案如下:
NSMutableArray *mutableVideoArray;
NSArray *videoArray = [[NSUserDefaults standardUserDefaults] arrayForKey:VIDEOKEY];
if (videoArray)
mutableVideoArray = [videoArray mutableCopy];
else
mutableVideoArray = [NSMutableArray array];
if (![mutableVideoArray containsObject:item])
{
[mutableVideoArray addObject:item];
[[NSUserDefaults standardUserDefaults] setObject:mutableVideoArray forKey:VIDEOKEY];
}
成功了,谢谢。将其存储为不可变数组更好,还是不会有任何区别?一旦存储它,这应该无关紧要——您放入NSUserDefaults系统的任何内容都将不可变地存储,即使它来自可变对象。很高兴它成功了!我正在修复一些出于同样原因挂起的旧应用程序。在我的情况下,它反过来工作,我必须另存为NSArray。iOS 8中会发生奇怪的事情:-(在我的例子中,它冻结在“[[NSUserDefaults standardUserDefaults]removeObjectForKey:key]”上。这对我来说真的很奇怪