gpt4 book ai didi

iphone - 数据保护开启 : standardUserdefaults corrupted after iOS restart

转载 作者:行者123 更新时间:2023-12-01 21:12:17 24 4
gpt4 key购买 nike

更新 1:当 iOS 的数据保护(即密码锁定)关闭时不会出现问题!

更新 2:禁用 ARC 时不会出现问题。

更新 3:在重新启动 iOS 之前杀死应用程序时不会发生问题。

我的 Settings 类使用 +initialize 实现了单例模式(加上代码以查看发生了什么):

@implementation Settings

static Settings* sharedSettings;
static NSUserDefaults* userDefaults;

+ (void)initialize
{
if ([Settings class] == self)
{
sharedSettings = [self new];
userDefaults = [NSUserDefaults standardUserDefaults];


// Code to see what's going on here ...
if (userDefaults == nil)
{
[[[UIAlertView alloc] initWithTitle:@"userDefaults == nil"
message:nil
delegate:nil
cancelButtonTitle:@"Close"
otherButtonTitles:nil] show];
}
else
{
if ([userDefaults objectForKey:@"Hello"] == nil)
{
[[[UIAlertView alloc] initWithTitle:@"Hello == nil"
message:nil
delegate:nil
cancelButtonTitle:@"Close"
otherButtonTitles:nil] show];
}
else if ([userDefaults boolForKey:@"Hello"] == NO)
{
[[[UIAlertView alloc] initWithTitle:@"Hello == NO"
message:nil
delegate:nil
cancelButtonTitle:@"Close"
otherButtonTitles:nil] show];
}

[userDefaults setBool:YES forKey:@"Hello"];
if ([userDefaults synchronize] == NO)
{
[[[UIAlertView alloc] initWithTitle:@"synchronize == NO"
message:nil
delegate:nil
cancelButtonTitle:@"Close"
otherButtonTitles:nil] show];
}
}
}
}

+ (id)allocWithZone:(NSZone*)zone
{
if (sharedSettings && [Settings class] == self)
{
[NSException raise:NSGenericException format:@"Duplicate Settings singleton creation"];
}

return [super allocWithZone:zone];
}

+ (Settings*)sharedSettings
{
return sharedSettings;
}

@end

我在我的 AppDeletate.m 中触发了这段代码(完全剥离):
#import "AppDelegate.h"
#import "Settings.h"

@implementation AppDelegate

- (BOOL)application:(UIApplication*)application didFinishLaunchingWithOptions:(NSDictionary*)launchOptions
{
[Settings sharedSettings];

self.window = [[UIWindow alloc] initWithFrame:[[UIScreen mainScreen] bounds]];
[self.window makeKeyAndVisible];

return YES;
}

@end

现在非常奇怪的是,在重新启动 iOS 后立即运行这个空应用程序时,我会同时得到“同步 == NO”和“Hello == nil”弹出窗口。然后当我杀死该应用程序并再次运行它时,一切都很好。
事实证明,当我使用 GCD 的 dispatch_after() 延迟 userDefaults = [NSUserDefaults standardUserDefaults] 和后续语句时(我做了 2 秒,但可能同样没问题),问题就消失了。
有人可以告诉我为什么会这样,或者这只是一些极端情况下的 iOS 错误或副作用???

补充:事实证明,当我在重新启动 iOS 之前杀死应用程序时,这个问题就消失了。这对我来说证明了它是 iOS 中的东西。

感谢收听!

科内利斯

ps:你可以相信我,我完全剥离了我的应用程序,只有三个模块:main.mm(标准XCode生成的单行代码)、AppDelegate.m(完整代码如上所示)和Settings.m(完整代码所示多于)。所以根本没有其他代码在运行。
当我进一步剥离它,只留下 AppDelegate.m 时,问题仍然存在。

最佳答案

+initialize 期间不应引用其他类.没有关于它何时运行以及当时存在哪些其他类的 promise 。 +initialize应该只做内部对类(class)的工作。

自添加 GCD 以来,这种单例模式已被取代。您应该出于各种原因使用 GCD 模式,其中之一是它在您认为它运行时运行。

How do I implement an Objective-C singleton that is compatible with ARC?

作为说明,我很好奇你的main.mm .制作顶级 ObjC++ 几乎总是一个坏主意,并且可能导致一些令人惊讶的副作用。 (ObjC++ 是一种古怪的胶水语言,具有许多奇怪的行为。您应该在尽可能少的类中使用它。)我个人会看看是否将其改回 .m解决了这个问题,虽然我仍然推荐 GCD-Singleton 而不是使用 +initialize .

关于iphone - 数据保护开启 : standardUserdefaults corrupted after iOS restart,我们在Stack Overflow上找到一个类似的问题: https://stackoverflow.com/questions/15450072/

24 4 0
Copyright 2021 - 2024 cfsdn All Rights Reserved 蜀ICP备2022000587号
广告合作:1813099741@qq.com 6ren.com