On Feb 16, 2012, at 12:05 PM, Greg Parker wrote:

> On Feb 16, 2012, at 8:22 AM, Matt Neuburg <m...@tidbits.com> wrote:
>> On Wed, 15 Feb 2012 16:20:50 -0800, Greg Parker <gpar...@apple.com> said:
>>> 
>>> Are you using GC or ARC? I think this is safe with GC but not safe with 
>>> ARC, but I'm not an expert in the NSNotificationCenter machinery.
>> 
>> ARC, but I don't see how it might be unsafe. I sure *hope* it isn't, because 
>> that's what the __weak is for. You need that because if your observer 
>> doesn't vanish in good order, neither will +self+, because the observer 
>> retains +self+, not just while registered with the notification center but 
>> for as long as it lives (by way of the block, I presume). *That* is 
>> something I *do* understand, having spent many hours watching the retain 
>> counts at work.
> 
> The question is, who retains the observer? The __block __weak variable does 
> not, because it's weak. NSNotificationCenter does not, as I understand it.

It does, actually; thanks for pressing me on this point.

That's why the easiest pattern under ARC for preventing a retain cycle in 
general (that is, where you - a view controller, say - hang on to a reference 
to the observer for a long time, like from viewWillAppear: to 
viewWillDisappear:) is to store it in a __weak ivar. When you unregister the 
observer (which you can do, because you have a reference to it in the ivar), 
the notification center releases it, it goes out of existence, the __weak ivar 
is automatically nilified, and (most important) the observer releases you, 
preventing a retain cycle.

Of course you could also solve the problem with a __strong ivar and nilify the 
ivar yourself after you unregister. But you don't have to, because the 
notification center retains the observer from the get-go. If it didn't, the 
__weak ivar would be nil when you need to unregister - and it isn't.

I've documented this (after a lot of experimentation - and did I mention "thank 
you, Instruments"???) here:

  http://www.apeth.com/iOSBook/ch12.html#_retain_cycles_and_weak_references

Naturally if you have any thoughts I would be *very* happy to hear them. m.

PS Oh, and if you'd like to play with the various possibilities, there's no 
need to write any code: I have a downloadable example project that demonstrates 
all of them:

<https://github.com/mattneub/Programming-iOS-4-Book-Examples/blob/master/convertedToIOS5/p229NotificationLeaker/p229NotificationLeaker/FlipsideViewController.m>

Set the ivar to __weak and leave the #define set at 1. Run the project. Flip 
the view and flip it back (with Done) and watch the Console. You'll see that 
observer is good and that we dealloc successfully.

--
matt neuburg, phd = m...@tidbits.com, http://www.apeth.net/matt/
pantes anthropoi tou eidenai oregontai phusei
Programming iOS 5! http://shop.oreilly.com/product/0636920023562.do
RubyFrontier! http://www.apeth.com/RubyFrontierDocs/default.html
TidBITS, Mac news and reviews since 1990, http://www.tidbits.com



_______________________________________________

Cocoa-dev mailing list (Cocoa-dev@lists.apple.com)

Please do not post admin requests or moderator comments to the list.
Contact the moderators at cocoa-dev-admins(at)lists.apple.com

Help/Unsubscribe/Update your Subscription:
https://lists.apple.com/mailman/options/cocoa-dev/archive%40mail-archive.com

This email sent to arch...@mail-archive.com

Reply via email to