On Jul 12, 2017, at 14:57 , Jeremy Hughes <moon.rab...@virginmedia.com> wrote:
> 
> I’m trying to understand memory management so I can avoid retain cycles and 
> other issues.

There’s nothing wrong with trying to understand. The bet you will (almost 
always) lose is one involving reasoning about *when* retain counts reach 
particular values (such as 1 or 0).

I may be overlooking something important, but I see basically three tasks you 
need to handle to avoid memory management bugs:

1. Strong references.

In terms of object lifetimes, these are the easiest, because an object A that 
depends on an object B’s existence and keeps a strong reference to B is doing 
the right thing. There’s nothing here to worry about, assuming the reference to 
B is released normally (and *automatically* usually) when A deallocates. What 
you do have to worry about are reference cycles. You must either use something 
like Instruments to find any, and either avoid creating them, or ensure that 
you break them manually at a suitable time.

2. Weak references.

This means zeroing weak references. (All weak references are zeroing since, 
IIRC, macOS 10.6.8.) Again, there’s nothing to do here, except to ensure that 
nothing crashes because a reference suddenly changes to nil.

3. Unowned/unsafe references.

These are the killers. Typically, these are delegate references, but it’s hard 
to keep track of all the possibilities. For example, NSWindow’s “delegate” is 
still AFAIK unsafe. It’s usually set to the window controller, but I’m not 
aware of any typical bugs arising from this reference becoming invalid. The 
most common problem I know of is from table and outline view delegate and data 
source references. In many cases, it’s wise to nil these out manually when 
(say) your window closes.

> I have a view hierarchy that is constructed programmatically.
> 
> This involves creating a view controller and a view, and then creating child 
> view controllers and views in a tree hierarchy. Child view controllers are 
> added to parent view controllers - so that (as I understand it) the parent 
> view controller owns the child view controller. Each view controller is given 
> a view, which it presumably owns, and each view is attached to a superview, 
> which also (presumably) owns the child view. So a view is owned by its view 
> controller and by its superview.
> 
> There is also a top-level view controller that comes from a nib.
> 
> If I release the child view controllers of this top-level view controller (by 
> assigning an empty array to childViewControllers), my expectation is that I 
> don’t have to release every view controller and view in the hierarchy because 
> they are effectively owned by the top-level view controller.

What you’re describing here is a hierarchy of strong references (in the “down” 
direction, with possibly weak references pointing “up”), so there’s not much to 
think about or do.

The real problem in this scenario is that the relationships between window and 
view controllers, windows and views of various types (not to mention a document 
instance in many cases) are extremely, messily intertwined, pretty much for 
ancient historical reasons. Trying to understand the *timing* of destruction in 
a window-closing scenario is hard, and if you do figure out what happened, 
you’ll end up thinking, “That’s weird, I wouldn’t have expected it to come out 
like that.”

I don’t know of any magic bullets for this, though someone else might jump in 
with more specific advice. My advice would be, simply choose a pattern for 
putting your apps’ UIs together, and stick to it.


_______________________________________________

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