SundayMonday
SundayMonday

Reputation: 19727

Objective-c: returning autoreleased object from method

What prevents the autoreleased instance of NSArray from being released before it's used in the method it's returned to?

- (NSArray *) f {
    return [NSArray array];
}

- (void) g {
    NSArray *a = [self f];
    // do something with a
}

Upvotes: 3

Views: 585

Answers (3)

bbum
bbum

Reputation: 162712

What prevents the autoreleased instance of NSArray from being released before it's used in the method it's returned to?

Autorelease pools are per thread. That is, an autoreleased object is, effectively, a delayed call to release that happens on a per thread basis.

Thus, if there is no call to drain between the caller and the callee, there is no way the autoreleased object will be released because of a pool drain (barring serious threading stupidity).

In general, pools are drained at very well specified times, like Kevin said:

• the run loop will drain the pool at the bottom of each pass through the loop

• dispatched blocks via GCD will execute within a pool context that'll be drained "every now and then" (implementation detail). NSOperationQueue behaves similarly

• other threads are responsible for doing it themselves

Thus, in your simple example, the code execution is quite linear and, by inspection, there can be no drain in that thread of execution between the return and the use in the caller.

(Note that this is also one of the reasons why retainCount is useless; it neither accounts for any "delayed release" calls caused by autorelease nor does it quantify any per-thread retains. In reality, you should think of retains/releases as being entirely per-thread; if you retain an object on a thread you should release it on the same thread unless you are explicitly transferring ownership from one thread to another.)

Upvotes: 5

Lily Ballard
Lily Ballard

Reputation: 185661

Autoreleased objects are only released when their surrounding pool is drained. This is not some magical process that happens behind the scenes. It's a deterministic event that happens at well-defined times. In general, the pool is drained when control returns to the run loop. If you establish your own nested pool, then you control when that drains.

Upvotes: 4

Phillip Mills
Phillip Mills

Reputation: 31016

The autorelease pool is drained during an iteration of the event loop. Since it's that drain that causes release messages to be sent to the autoreleased objects, they are still valid in the calling method.

Upvotes: 2

Related Questions