Reputation: 20376
I have a few basic questions regarding the syntax and usage of properties in Objective C:
Assume the following declaration in the header:
@interface TestObject : NSObject {
NSArray *myArray;
}
@property (nonatomic, retain) NSArray *myArray;
In the implementation, can I:
myArray
and self.myArray
interchangeably for setting and getting purposes?self.myArray = nil
equivalent to [myArray release]
?self.myArray = nil
rather than [myArray release]
?Upvotes: 4
Views: 283
Reputation: 7332
Both existing answers are wrong.
@synthesize generates setters and getters that look like this:
- (void)setMyArray:(NSArray*)array {
if( myArray != array ) {
[myArray release];
myArray = [array retain];
}
}
- (NSArray*)myArray {
return myArray;
}
(Note, they aren't exactly like this, and differ if you specify copy, or other attributes, but that's the basic formula). Now we can see that self.myArray = nil;
WILL release the old array. self.myArray and myArray aren't interchangeable for setting purposes. Moreover, self.myArray = nil;
will continue to work in a garbage collected world.
As Dave Delong points out, self.myArray = nil will notify anyone observing myArray of the changed value, which could be a problem if you do this in your dealloc method. To avoid this case your dealloc would look something like:
- (void)dealloc {
[myArray release]; myArray = nil;
[super dealloc];
}
(note myArray = nil;
is a stylistic choice here.)
Upvotes: 4
Reputation: 14824
myArray
and self.myArray
are actually different. myArray
is accessing the variable directly, whereas self.myArray
(which is equivalent to [self myArray]
) is calling an accessor method. Most people agree that you should use self.myArray
(or [self myArray]
) all the time, and never use myArray
directly. This is because the accessor might have side effects; for example, KVO won't work if you set your variable directly, and memory management won't be handled for you.
Your property is declared with retain
, so self.myArray = anArray
(which is the same as [self setMyArray:anArray]
) does the following:
Therefore, when you do self.myArray = nil
, one of the steps (#2) is indeed release the old array. (And since the new one is nil
, we don't have to worry about its memory management, even though we retained it.) So yes, self.myArray = nil
is a valid way of releasing myArray
.
HOWEVER, if you're talking about releasing myArray
in dealloc
, it's generally a good idea to use [myArray release]
, because calling self.myArray = nil
will have side effects if any other objects are observing myArray
through KVO. So while it does follow memory management standards, it's not a good idea to write your dealloc
method using self.myArray = nil
.
Upvotes: 5
Reputation: 4200
To setup setters/getters you'd have to implement those in main as:
+ (NSArray*) myArray {
return myArray;
}
+ (void) setMyArray:(NSArray*)input{
myArray = input;
}
Upvotes: -3