Memory Management
To properly manage memory, Cocoa
provides a reference
counting
mechanism, supported by the
NSObject
and NSAutoreleasePool
classes. As its name suggests, reference counting maintains a count
of how many references there are to an object—indicating how
many other objects are interested in keeping the object around.
Reference counting is not automatic; the compiler has no way to
determine an object’s lifetime. Therefore, the
following NSObject
reference counting methods must
be called to indicate the level of interest in an object to the
memory management system:
-
retain
Increments the object’s reference count by
1
. When you want to register interest in an object that you did not create or copy, indicate interest in it by calling this method.-
release
Decrements the object’s reference count by
1
. This message is sent to objects created with thealloc
method or sent aretain
message when you are no longer interested in using them. If this causes the retain count to reach0
, the runtime deallocates the object.-
autorelease
Adds the object to the current autorelease pool . This allows you to release your interest in an object without immediately causing the retain count to reach
0
. When the autorelease pool is itself released, it sends therelease
message to every object it contains. This is most useful when you want to pass the object to another object as a return value and won’t have the opportunity to release the object later by yourself.
The following set of rules will help you perform accurate reference counting and avoid either leaking memory or prematurely destroying objects:
Objects created by
alloc
orcopy
have a retain count of1
.If you want to keep an object received from another mechanism, send it a
retain
message.When you are done with an object created by
alloc
orcopy
, or retained by theretain
message, send it arelease
message.When you add an object to a collection, such as an array or dictionary (described in Chapter 2), the collection retains it. You are no longer responsible for the object, and you may safely release any interest in it.
If you need to release interest in an object but need to ensure that it is not immediately destroyed, send an
autorelease
message so the object is put in the autorelease pool for later release.
Warning
Once you have released interest in an object, you
shouldn’t send any messages to it. If an object is
deallocated because its retain count reached 0
,
sending a message to the object will cause an error.
Retaining Objects in Accessor Methods
Accessor
methods require a bit of caution, especially those where an
object’s instance variables are set. Because an
object passed to a set method may already be held, you must be
careful about how memory management is performed. Releasing an object
before retaining it can lead to unfortunate side effects and can be
the source of much frustration. To ensure that memory management is
performed correctly, send the autorelease
method
to an old object reference before replacing it with a new reference.
Example 1-8 shows how this rule is applied in the
Song
class’s
setTitle
: method.
Another way to ensure proper memory management and further increase
encapsulation is to make a copy of the parameter, as shown in Example 1-9. This ensures that even if a mutable subtype
of NSString
were given, any modifications to that
parameter would not change the contents of the
title
variable.
These practices ensure proper memory management in almost all situations you are likely to encounter. However, some fringe cases require care in handling. For more details, see http://www.stepwise.com/Articles/Technical/2002-06-11.01.html.
Get Cocoa in a Nutshell now with the O’Reilly learning platform.
O’Reilly members experience books, live events, courses curated by job role, and more from O’Reilly and nearly 200 top publishers.