- [CALayer retain]:发送到解除分配实例的消息

时间:2010-07-13 09:47:13

标签: iphone calayer nsautoreleasepool nszombie

我正在开发一款iphone应用程序,当我打开我的NSZombieEnabled时,我经常会因错误而崩溃:

*** -[CALayer retain]: message sent to deallocated instance 0xe6012e0

当我在视图控制器中推送或弹出视图时,总是会出现这种情况。有时会出现此错误:

-[UIApplication endIgnoringInteractionEvents] called without matching -beginIgnoringInteractionEvents. Ignoring.

这是什么意思?任何人都有线索或遇到过这个问题?

非常感谢您的帮助!

罗曼

3 个答案:

答案 0 :(得分:14)

这可能意味着您正在尝试将对象保留为已释放的UI对象,例如UIButton。有很多方法可以追踪这个问题但是如果你可以缩小应用程序中发生这种情况的范围,我通常会开始评论版本,直到我看到问题发布的位置。我的猜测是你发布了一些自动释放的东西。

答案 1 :(得分:1)

我想要的不仅仅是@Tony的答案。因为它是正确的。

您可能正在使用UI object's layer或其sublayer。所以只需检查实际上UI在使用之前没有发布;

if(UI object) //has instance
{
   //now use UI object.
}

答案 2 :(得分:1)

如果上述答案无效,请检查您的代码是否在收到此错误的类中使用KVO。当KVO向您的观察类发送关于密钥更改的值的消息时,如果该类已被ARC释放,那么KVO将尝试警告内存中不存在的有关该更改的地址,从而导致您的应用程序抛出此错误。

考虑一下,这是一个名为MyViewController的类,您希望观察它bounds view.layer属性的变化,指示布局从横向更改为纵向。所以你添加一行:

// self is MyViewController
self.view.layer.addObserver(self, forKeyPath: "bounds", options: .new, context: nil)

如果view尺寸发生变化,这会提醒您的班级。

但是如果你的viewController被解雇,比如说UINavigationController将它弹出堆栈,KVO仍然会尝试提醒MyViewController视图的界限已经改变(因为现在它&# 39;消失了)。然后,当KVO执行此操作时,您的应用程序将崩溃。在调试控制台中,您将看到以下消息:

-[MyViewController retain]: message sent to deallocated instance

这是因为您必须删除该keyPath的观察者(MyViewController)。最好在MyViewController被解雇之前执行此操作,因此:

override func viewWillDisappear(_ animated: Bool) {
    super.viewWillDisappear(animated)
    self.view.layer.removeObserver(self, forKeyPath: "bounds")
}

现在,当您尝试从导航堆栈中弹出MyViewController时,将不会出现错误。