如果我不再使用它,为啥在释放 MKMapView 后我会崩溃?

Posted

技术标签:

【中文标题】如果我不再使用它,为啥在释放 MKMapView 后我会崩溃?【英文标题】:Why am I crashing after MKMapView is freed if I'm no longer using it?如果我不再使用它,为什么在释放 MKMapView 后我会崩溃? 【发布时间】:2011-01-12 09:15:08 【问题描述】:

我有一个MKMapView。有时在我的视图控制器被关闭后,我会得到一个EXC_BAD_ACCESS

我打开了NSSZombies,它看起来像MKMapView 的委托——我的视图控制器! — 被调用,尽管MKMapViewUIViewController 子类都被释放了。我检查过了,我的内存管理是正确的。

发生了什么事?

【问题讨论】:

【参考方案1】:

这是因为MKMapView 的工作方式。有一个操作挂起,所以 MapKit 保留了 MKMapView,它实际上还没有被释放。这本身不是问题。问题是它仍在向您的代表发送消息。

解决方法很简单:作为视图控制器清理的一部分,将地图视图的代理设置为nil,这将阻止MKMapView 向其发送消息。

这记录在MKMapViewDelegate Protocol Reference:

在释放您已为其设置委托的 MKMapView 对象之前,请记住将该对象的委托属性设置为 nil。您可以在其中处理地图视图的 dealloc 方法中执行此操作。

编辑:也给 Oscar 一个赞成票,就在下方,谁在这里提供了文档报价。

鉴于 ARC,我建议这意味着您应该在视图控制器的 dealloc 中将地图视图的委托设置为 nil

【讨论】:

非常感谢您的帮助! 谢谢。我的问题是我们是否应该以某种方式知道这一点。如果这是 MapView 用户所期望的,那么为什么我们不必清除所有接受委托的控件的委托指针? 谢谢!这节省了我的时间。【参考方案2】:

好的,这是对答案的确认。它来自 Apple 文档,但 MKMapView 中缺少它。它只能在其委托协议的文档中找到:

在释放您设置了一个 MKMapView 对象之前 委托,记得将该对象的委托属性设置为 nil。一 你可以这样做的地方是你处理的 dealloc 方法 地图视图。

注意:这也适用于 UIWebView。

我在委托的 dealloc 方法中将 MapView 的委托指针设置为 nil,我们的崩溃似乎已经消除。

【讨论】:

我不知道 Apple 在任何地方都记录了这种行为。谢谢;我已将链接添加到我的答案中(其中也包含了它的原因)。【参考方案3】:

将地图视图的代理设置为nil 对我不起作用。但是,在代理上设置 showsUserLocation=NO 可以确保没有收到位置更新。

【讨论】:

您是否连接了地图视图?我猜它是零。【参考方案4】:

就我而言,问题是我第一次启动应用时在提示位置授权时没有按“允许”(不小心!!)。

卸载应用程序并重新安装它,当出现提示时我允许授权并且不再崩溃!

【讨论】:

以上是关于如果我不再使用它,为啥在释放 MKMapView 后我会崩溃?的主要内容,如果未能解决你的问题,请参考以下文章

MapKit (MKMapView):zPosition 在 iOS11 上不再工作

为啥 MKMapView 不显示当前位置红色图钉?

为啥你必须在 ios8 中删除观察者?

为啥在释放指向它的指针后仍然可以访问结构的成员?

为啥 MKMapView 用户 Location 属性是垃圾......一段时间?

如果在添加注释时缩放,MKMapView 会崩溃