UIAlertView 在未记录的方法上崩溃

Posted

技术标签:

【中文标题】UIAlertView 在未记录的方法上崩溃【英文标题】:UIAlertView crashing on undocumented method 【发布时间】:2011-02-04 13:58:41 【问题描述】:

由于一个难以捉摸的错误,我们的应用程序崩溃的频率约为 1,500 次启动中的 1 次。包括堆栈跟踪的相关部分。它作为回调被触发,所以我没有参考它在我自己的代码中发生的位置。

看起来正在发生的事情是有一个 UIViewAnimationState 对象正在调用 UIAlertView's 私有方法 (_popoutAnimationDidStop:finished:)。唯一的问题是,此时UIAlertView 似乎已被释放。我不会对警报视图做任何奇怪的事情。我把它们扔了,我等待用户输入。它们都是在发布之前显示的。

有人遇到过吗?在这一点上,我倾向于它是一个 Apple 错误。

Thread 0 Crashed:
0   libobjc.A.dylib                 0x3138cec0 objc_msgSend + 24
1   UIKit                           0x326258c4 -[UIAlertView(Private) _popoutAnimationDidStop:finished:]
2   UIKit                           0x324fad70 -[UIViewAnimationState sendDelegateAnimationDidStop:finished:]
3   UIKit                           0x324fac08 -[UIViewAnimationState animationDidStop:finished:]
4   QuartzCore                      0x311db05c run_animation_cal

lbacks

【问题讨论】:

你还记得调试器中收到的错误吗?是否可能:[* respondsToSelector:]: 消息发送到已释放实例 【参考方案1】:

UIAlertView 可能会在其委托被释放后尝试调用其委托上的方法。为了防止这种类型的错误,每当您将一个对象设置为另一个对象的委托时,请在委托对象的 dealloc 方法中将委托属性设置为 nil。例如


@implementation YourViewController
@synthesize yourAlertView;

- (void)dealloc 
    yourAlertView.delegate = nil; // Ensures subsequent delegate method calls won't crash
    self.yourAlertView = nil; // Releases if @property (retain)
    [super dealloc];


- (IBAction)someAction 
    self.yourAlertView = [[[UIAlertView alloc] initWithTitle:@"Pushed"
                         message:@"You pushed a button"
                         delegate:self
                         cancelButtonTitle:@"OK"
                         otherButtonTitles:nil] autorelease];
    [self.yourAlertView show];


// ...

@end

【讨论】:

非常感谢。明显的解决方案,我只是假设它是 UIAlertView 以某种方式过早地被释放了。有时你只需要换一双眼睛看看它。对于遇到此问题的任何其他人,请注意,如果您使用的导航堆栈可以从非确定性地推送/弹出(例如在连接丢失时),您需要始终取消设置您的 dealloc 中的任何委托。 Apple 没有在他们的示例项目中正确说明这种模式。 我面临同样的问题,有人可以指出当 AlertView 声明为局部变量时如何解决这个问题。我们必须在委托回调中将委托设置为 nil 吗? 有趣的是,即使在以 ARC 模式编译的应用程序中也会发生这种情况。为什么 Apple 没有像他们对所有类似委托的属性所推荐的那样将 UIAlertView 的委托属性设为安全弱?

以上是关于UIAlertView 在未记录的方法上崩溃的主要内容,如果未能解决你的问题,请参考以下文章

UIAlertView 的私有方法崩溃

如何在未处理的任务异常上崩溃?

iOS7上的UIAlertView崩溃私有方法

应用程序在 [UIAlertView 显示] 上崩溃

为啥在我的视图被推送到导航堆栈之前我的 UIAlertView 没有在屏幕上消失?

UIAlertView 崩溃应用