在iPhone的Objective-c世界中,我到处都看到了这种模式,我一直在自己使用它,却没有真正理解发生了什么:
在Test.h中
@interface Test: UIViewController
{
NSMutableArray *testArray;
}
@property (retain, nonatomic) NSMutableArray *testArray;
在Test.m中
@implementation Test
@synthesize testArray
- (void) viewDidLoad
{
// why do we do this?
NSMutableArray *init = [[NSMutableArray alloc] init];
self.testArray = init;
[init release];
[self.testArray addObject: @"A"]; // why can't I do this directly?
...
}
- (void) dealloc
{
[testArray release];
[super dealloc];
}
我的问题是:如果testArray在属性中声明时有一个保留,为什么我们需要创建一个新的NSMutableArray init对象,将其分配给testArray并释放?为什么我不能在viewDidLoad中开始使用testArray而不做其他事情?
我知道对于这样做的最佳方式存在争议(创建一个新对象,或者使用自动释放对象),但在这两种情况下,我们最终得到的testArray的保留计数为1.我相信'保留'财产已经给了它。那么为什么需要创建这个init对象呢?
答案 0 :(得分:7)
'retain'属性不会自动为您创建NSMutableArray。相反,它只是表明无论何时做为该属性分配内容,它都将被保留。
如果你的代码是这样的话:
- (void) viewDidLoad
{
[self.testArray addObject: @"A"];
}
然后self.testArray将是nil
,因此它本质上是一个无操作。在你为self.testArray指定一些内容之前,它是空的。
这是发生了什么。
- (void) viewDidLoad
{
// we need to assign an NSMutableArray to self.testArray.
NSMutableArray *init = [[NSMutableArray alloc] init];
// The array has been retained once (by the call to |alloc|)
self.testArray = init;
// The array is assigned to a property with the 'retain' attribute
// Thus, the array has now been retained twice
[init release];
// We release the array, so it now is retained once.
// We now have an array in self.testArray, so we can add something to it.
[self.testArray addObject: @"A"];
}
答案 1 :(得分:1)
@property指令中的“retain”指定setter应保留输入值,而不是简单地复制值。它与分配(留出内存)和初始化(构造对象)对象无关。保留在@property指令上只需在调用setter时增加保留计数(这会让你做一些像self.myobject这样的东西而不专门调用retain。