If a child object is released in the dealloc of a parent object, why would the child object's weak reference to the parent be nil*

房东的猫 提交于 2020-01-07 09:09:07

问题


*because the child is released within the dealloc of the parent, wouldn't that imply that the parent object still exists, and that the child's weak reference back to the parent should still be valid?

I have a parent object, a NSViewController subclass, which owns another object, a NSWindowController subclass.

@interface MyViewController : NSViewController
@property (strong) MyWindowController *myWindowController;

The NSWindowController subclass has a weak reference back to the NSViewController

@interface MyWindowController : NSWindowController
@property (weak) MyViewController *myViewController;

Inside of MyViewController, I have overridden -dealloc:

-(void)dealloc
{
   [self.myWindowController close];
   self.myWindowController = nil;
}

And inside of MyWindowController, I am adding/removing observers inside of the init/close methods.

//INIT:
[self.myViewController addObserver:self forKeyPath:NSStringFromSelector(@selector(selectedObjects)) options:kObservingOptions context:nil];


//CLOSE:
[self.myViewController removeObserver:self forKeyPath:NSStringFromSelector(@selector(selectedObjects))];

Now here's the confusing part.

The order of operations on deallocation goes like this:

  • -[MyViewController dealloc]
  • -[MyWindowController close]
  • -[MyViewController removeObserver:MyWindowController]

BUT, at the point of -[MyWindowController close], the weak reference to MyViewController is nil. Even though it was MyViewController that called close in the first place.

This causes issues because the observer isn't properly removed, and later throws exceptions and sometimes even crashes.

What it looks like, is that the retain count to MyViewController had already been decremented to 0 before the -dealloc is called, so MyWindowController's weak reference to it gets set to nil. But that doesn't make sense to me because it would seem like the retain count would decrement after -dealloc, and also even if that weren't the case, would the weak reference be nil?

It may be possible that this is just a weird interaction w/ NSViewController owning a NSWindowController, but that doesn't make much sense to me either

Why is the weak @property == nil?


回答1:


From Apple's documentation on ARC:

A weak reference does not extend the lifetime of the object it points to, and automatically becomes nil when there are no strong references to the object.

Note, that it doesn't say "when an object is deallocated." If an objects dealloc method is being called, then all strong references have, by definition, been removed.

Furthermore, you shouldn't be calling methods on objects that have already been deallocated. You should find a way to unregister your observer before the object is deallocated.



来源:https://stackoverflow.com/questions/33224893/if-a-child-object-is-released-in-the-dealloc-of-a-parent-object-why-would-the-c

易学教程内所有资源均来自网络或用户发布的内容,如有违反法律规定的内容欢迎反馈
该文章没有解决你所遇到的问题?点击提问,说说你的问题,让更多的人一起探讨吧!