该项目适用于 iOS 5.0。我已经设置了自动引用计数,无论如何如果我写了一个保留语句,我就无法编译代码。
我在一个函数中写了一个开关,因为我不想创建 if 和很多 if else 分支。
我的代码部分相对简单并且看起来正确,但似乎只是:
NSUserDefaults* userDefaults = [NSUserDefaults standardUserDefaults];
switch (selectedRow) {
case 0://English
[userDefaults setObject:@"English" forKey:@"language"];
break;
case 1:// Deutsch
[userDefaults setObject:@"German" forKey:@"language"];
break;
case 2://Français
[userDefaults setObject:@"French" forKey:@"language"];
break;
case 3://Italiano
[userDefaults setObject:@"Italian" forKey:@"language"];
break;
case 4://Español
[userDefaults setObject:@"Spanish" forKey:@"language"];
break;
default:
break;
}
// flush:
[userDefaults synchronize];
在运行时我收到这条消息: *** -[MyClass retain]: message sent to deallocated instance 0x6e78580 并且它将在某些情况下分支的 [userDefaults setObject 行将 XCode 显示为断线。
我在某处看到编译 Switch 时会创建一个类。但我不确定使用哪种语言:Java、C# 或 Obj-C,并且因为我离开了我的课程并且我正在执行 switch 类,它将释放 userDefaults 变量,这就是释放 userDefaults 对象的原因。现在我不知道如何编写这个开关来开始工作并且看起来很专业。我不想在每种情况下都创建 userDefaults 变量并在那里刷新。唯一的解决方案是将此开关写入 if-else?
这是有效的:
NSUserDefaults* userDefaults = [NSUserDefaults standardUserDefaults];
switch (selectedRow) {
case 0://English
{
[userDefaults setObject:@"English" forKey:@"language"];
}
break;
case 1:// Deutsch
{
[userDefaults setObject:@"German" forKey:@"language"];
}
break;
case 2://Français
{
[userDefaults setObject:@"French" forKey:@"language"];
}
break;
case 3://Italiano
{
[userDefaults setObject:@"Italian" forKey:@"language"];
}
break;
case 4://Español
{
[userDefaults setObject:@"Spanish" forKey:@"language"];
}
break;
default:
break;
}
// flush:
[userDefaults synchronize];
为什么?
不知道为什么它确实有效,但它又崩溃了。我已经在代码中移动了变量:
开关(选定行){
case 0://English { NSUserDefaults* userDefaults = [NSUserDefaults standardUserDefaults]; [userDefaults setObject:@"English" forKey:@"language"]; // flush: [userDefaults synchronize]; } break; case 1:// Deutsch { NSUserDefaults* userDefaults = [NSUserDefaults standardUserDefaults]; [userDefaults setObject:@"German" forKey:@"language"]; // flush: [userDefaults synchronize]; } break; case 2://Français { NSUserDefaults* userDefaults = [NSUserDefaults standardUserDefaults]; [userDefaults setObject:@"French" forKey:@"language"]; // flush: [userDefaults synchronize]; } break; case 3://Italiano { NSUserDefaults* userDefaults = [NSUserDefaults standardUserDefaults]; [userDefaults setObject:@"Italian" forKey:@"language"]; // flush: [userDefaults synchronize]; } break; case 4://Español { NSUserDefaults* userDefaults = [NSUserDefaults standardUserDefaults]; [userDefaults setObject:@"Spanish" forKey:@"language"]; // flush: [userDefaults synchronize]; } break; default: break; }
这又崩溃了,我来这里检查答案
我看到了下面的建议:
NSArray * languages = [NSArray arrayWithObjects: @"English", @"German", @"French",@"Italian", @"Spanish", nil];
NSString * selectedLanguage = [languages objectAtIndex: selectedRow];
[[NSUserDefaults standardUserDefaults] setObject: selectedLanguage forKey:@"language"];
这次崩溃在同一行:
[[NSUserDefaults standardUserDefaults] setObject: selectedLanguage forKey:@"language"];
- 怎么了?不敢相信。*** -[MyClass retain]:消息发送到释放的实例 0x6b532c0
MyClass 是一个 UIViewContoller。我进行语言选择并按一些按钮导航 1 或 2 屏幕,然后我回来并再次进行语言选择,它会崩溃,但并非总是如此。但是当它崩溃时总是在同一行并且总是相同的错误消息。
有什么
userDefaults setObject
带导航?
#------------------------------------------------ -- 得到真正的问题:比找到解决方案容易#------------------------------------ ---------------
我写了:userDefaults setObject 我还写了:这是一个 ARC 项目,它在 MyClass 保留失败,这不能是我的代码。
代码是带有操作表的语言选择。如果我进行搜索,我将获得下一个链接: EXC_BAD_ACCESS invoking a block
- 从那里我看到我应该在某处生成一个副本而不是保留。问题是为什么需要在 setObject 处保留?好吧,因为它添加了一个更改侦听器...
//[[NSUserDefaults standardUserDefaults] addObserver:self forKeyPath:@"language" options:NSKeyValueObservingOptionNew context:NULL];
代码被删除并且回调的内容在切换代码之后移动了它解决了问题 - 不需要保留来做回调