开发者

Objective-C Accessor Methods and Use of Autorelease

I've been reading an apple document on Memory Management and am now a bit confused regarding the recommended implementation of Accessors. Apple cites 3 approaches in implementing accessors.

Technique 1

I've copied the code from the first technique which reflects: "Getter retains and autoreleases the value before returning it; setter releases the old value and retains (or copies) the new value." This first technique is stated to be more robust but suffers performance penalties on frequently called getters.

- (NSString*) title {
    return [[title retain] autorelease];
}

- (void) setTitle: (NSString*) newTitle {
    if (title != newTitle) {
        [title release];
        title = [newTitle retain]; // Or copy, depending on you开发者_如何学Pythonr needs.
    }
}

skipping Technique 2

Technique 3

The third technique is better for frequently called setters and getters. This is also the method I've always followed.

- (NSString*) title {
    return title;
}

- (void) setTitle: (NSString*) newTitle {
    if (newTitle != title) {
        [title release];
        title = [newTitle retain]; // Or copy, depending on your needs.
    }
}

My questions are:

  1. (Technique 1) The setter first releases the existing value even if it doesn't point to anything. This would send a message to nil which I understand is supported in Objective-C but still looks odd. Am I understanding this correctly?

  2. (Technique 1) Why is the retain stacked inside an autorelease?

  3. (Technique 1) Is the caller whom uses the getter expected to call release after they're done with the object?

The apple developer documentation page can be found at: Memory Management Programming Guide - Accessor Methods


(Technique 1) The setter first releases the existing value even if it doesn't point to anything. This would send a message to nil which I understand is supported in Objective-C but still looks odd. Am I understanding this correctly?

Yup. Messages to nil matter not.

(Technique 1) Why is the retain stacked inside an autorelease?

That guarantees that the following doesn't break:

x = [foo title];
[foo setTitle: @"bar"];
[x length]; // x has been released, possibly, if -title didn't retain/autorelease

(Technique 1) Is the caller whom uses the getter expected to call release after they're done with the object?

No.



  1. Sending a message to nil is defined to do nothing. This setter is an excellent example of how that allows you to write simpler code: [title release] instead of if (title != nil) [title release];. Note also that no special checks for nil are necessary on newTitle.

  2. The retain/autorelease pair in the getter mean that the returned object will remain valid through the lifetime of the current function call (technically, until the autorelease pool is drained), even if the setter is called. The documentation you cite gives an example of how that can be helpful if there's a variable with a "non-owning reference" to the value.

  3. NO. The value has already been autoreleased; caller must not release it again.

0

上一篇:

下一篇:

精彩评论

暂无评论...
验证码 换一张
取 消

最新问答

问答排行榜