-1

Once I forgot to call "removeObserver:forKeyPath:" when I was using KVO. On iOS10 simulator, the simulator crashed. But on iOS11 simulator, everything was normal. There's no memory leak and no crash.

I'm confused why not calling "removeObserver:forKeyPath:" leads to different results on different SDK versions.

Here's demo code:

#import <UIKit/UIKit.h>
@interface GSObject : NSObject

@end
@interface GSObject ()

@property (nonatomic, assign) NSInteger integer;

@end

@implementation GSObject

- (instancetype)init {
    if (self = [super init]) {
        [self addObserver:self forKeyPath:@"integer" options:NSKeyValueObservingOptionInitial context:nil];
    }
    return self;
}

- (void)observeValueForKeyPath:(NSString *)keyPath ofObject:(id)object 
change:(NSDictionary<NSKeyValueChangeKey,id> *)change context:(void 
*)context {
    NSLog(@"%@",object);
}
@end

int main(int argc, char * argv[]) {
    @autoreleasepool {
        GSObject *object = [[GSObject alloc] init];
        object = nil;
    }
}
CoyBit
  • 1,592
  • 1
  • 17
  • 19
Johnson
  • 3
  • 2

1 Answers1

2

I'm confused why I didn't call "removeObserver:forKeyPath:" it shows different result on different sdk version.

That would be because different SDK versions are different. They behave differently. That is what “different” means.

Please read the release notes, https://developer.apple.com/library/archive/releasenotes/Foundation/RN-Foundation/index.html :

Prior to 10.13 [and iOS 11], KVO would throw an exception if any observers were still registered after an autonotifying object's -dealloc finished running.

matt
  • 515,959
  • 87
  • 875
  • 1,141