分配 mapView 时随机 KVO 块崩溃,仅在 open/close 屏幕多次时发生

Random KVO block crashes when allocating mapView, happens only when open/close screen several times

应用程序在地图屏幕上多次打开和关闭时会崩溃。 (主要是在第 6 次尝试时)

Class 继承自 GMSMapView

class AirportMapView: GMSMapView , AirportMapViewProtocol{

weak var airportMapViewModuleDelegate: AirportMapViewModuleProtocol?

required init?(coder aDecoder: NSCoder) {
    super.init(coder: aDecoder)
 }
override init(frame: CGRect) {
    super.init(frame: frame)
 }
convenience init(from frame: CGRect, with cameraPosition: GMSCameraPosition) {
    self.init(frame: frame)
    self.camera = cameraPosition
 }
  func setCluster() {

    let algorithm = CustomGoogleMapsClusteringAlgorithm.init();
    mapIconGenerator = VJAirportIconGrayClusterGenerator.init()
    let renderer = VJGoogleMapsClusterRenderer(mapView: self,
                                               clusterIconGenerator: mapIconGenerator!)
    clusterManager = GMUClusterManager.init(map: self, algorithm: algorithm, renderer: renderer)
    clusterManager?.setDelegate(self, mapDelegate: self)

 }
}

在ViewControllerviewDidLoad中调用mapViewinit方法

self.mapView = [[AirportMapView alloc] initFrom:frame with:camera];
self.mapView.myLocationEnabled = YES;
self.mapView.settings.compassButton = YES;
self.mapView.settings.zoomGestures = YES;
self.mapView.airportMapViewModuleDelegate = self;

附加的崩溃回溯和控制台日志

观察:

我在自定义 UIView 子类中遇到了与 GMSMapView 类似的问题

var mapView: GMSMapView!
var clusterManager: GMUClusterManager!

在 GMUClusterManager 中的 dealloc 之前被释放,这会导致崩溃,因为在调用 removeObserver 之前 mapView 将变为 nil 所以我添加了

deinit {
    clusterManager = nil
}

到我的 UIView 子类

检查此线程 https://github.com/googlemaps/google-maps-ios-utils/issues/181#issuecomment-385531638

在检查了 Google-Maps-iOS-Utils 源代码后,发现 GMSClusterManager class 没有保持对它通过 KVO 观察到的 GMSMapView 的强引用。如果在 dealloc.

调用 removeObserver:forKeyPath: 方法之前释放 GMSMapView 对象,这可能会导致崩溃

根据 Apple documentation,应该为通过 KVO 观察到的对象维护强引用:

Note: The key-value observing addObserver:forKeyPath:options:context: method does not maintain strong references to the observing object, the observed objects, or the context. You should ensure that you maintain strong references to the observing, and observed, objects, and the context as necessary.

有关详细信息,请参阅 this pull request(现已合并)。

几乎相同的崩溃...当我将 clusterManager 从强 属性 更改为堆栈对象

时它消失了