不小心重写了父类的某个方法导致的崩溃
ZAEButton类里有一个commonInit方法,该方法会注册KVO “enabled”.
1 2 3 4 5 6 7 8 9 10 11 12 13 14 15 16 17 18 19 20
| - (instancetype)initWithFrame:(CGRect)frame { self = [super initWithFrame:frame]; if (self) { [self commonInit]; } return self; }
- (void)commonInit { [self addObserver:self forKeyPath:@"enabled" options:NSKeyValueObservingOptionOld | NSKeyValueObservingOptionNew context:nil]; }
- (void)dealloc { [self removeObserver:self forKeyPath:@"enabled"]; }
|
ZAECountDownButton类为ZAEButton的子类,如果不仔细看父类的实现的话,可能也会定义一个commonInit方法.此时就是重写了该方法,虽然这并不是你的意愿.
1 2 3 4 5 6 7 8 9 10 11 12 13 14 15 16 17 18 19 20
| - (instancetype)initWithFrame:(CGRect)frame { self = [super initWithFrame:frame]; if (self) { [self commonInit]; } return self; }
- (void)commonInit { _duration = 30; _autoCountDown = YES; _timerStartState = ZAECountDownButtonTimerStartStateFromBegining; [self addTarget:self action:@selector(buttonDidClicked:) forControlEvents:UIControlEventTouchUpInside]; _activityView = [[UIActivityIndicatorView alloc] initWithActivityIndicatorStyle:UIActivityIndicatorViewStyleGray]; [self addSubview:_activityView]; _activityView.center = CGPointMake(self.bounds.size.width/2.0, self.bounds.size.height/2.0); }
|
崩溃就这样产生了:
当实例化一个ZAECountDownButton对象,调用到[super initWithFrame:frame]时,由于子类和父类都有一个commonInit方法,子类会覆盖父类的方法,最终调用的是子类的commonInit方法.此时,子类就不会注册kvo,而当对象销毁时,会执行到父类的dealloc方法移除KVO,于是程序会因为KVO注册—移除不匹配而导致崩溃.
这或许就是有些框架中父类的初始化方法都有”_”的缘故吧.