当我“自动释放”对象并从方法中返回它时,我应该在调用重新调整对象的方法的“父方法”中“释放”它吗?
不,这就是为什么。让我们完全按照您所说的来布局一个示例:
-(NSObject*)someMethodThatReturnsAnAutoreleasedObject {
return [[[NSObject alloc]init]autorelease];
}
-(void)myMethod {
NSObject *obj = [self someMethodThatReturnsAnAutoreleasedObject];
[obj doSomething];
[obj release] //PROBLEM!
}
逐步查看对象的保留计数,您会发现虽然-autorelease
可能不会立即对您造成问题,但它会在以后的某个日期(因为-autorelease
'd 对象不是“自动释放”,而是当他们拥有的池被耗尽或解除分配时,他们被集体解除分配)。返回自动释放对象的方法返回的最终保留计数为 0 (0 (start) + 1 (alloc) - 1 (autorelease)),因此释放它不仅没有必要,而且会导致崩溃。
第二个问题是,我从方法(另一个对象上的实例方法,fe userService)返回对象(fe user)并将其保存到属性(self.userProp,自我实例化对象 userService 并调用他的方法)。当我释放对象 userService(其方法返回对象用户,存储在属性 self.userProp 中)时,它也释放了存储在属性中的对象(对象用户存储在属性 self.userProp 中)。为什么?谁是财产对象的所有者?
再次,首先进行一些设置(起初这相当复杂,但在你看到你在做什么之后完全有意义)。
-(NSUserService*)someMethodThatReturnsAnAutoreleasedObject {
return [[[NSUserService alloc]init]autorelease];
}
-(void)myMethod {
self.userservice = [self someMethodThatReturnsAnAutoreleasedObject];
[obj doSomething];
[obj release] //No problem, assuming userService is declared retain or strong.
}
好吧,为什么这不一样?内存限定符,这就是原因!当你声明一个属性时,你声明了一组内存限定符来告诉编译器什么样的修饰符要附加到赋值符号上。大多数属性是声明的retain
或强的((在 ARC 下),并且希望你的属性也是userService
这样声明的)如果它们是对象类型,这会使编译器解释
self.userservice = [self someMethodThatReturnsAnAutoreleasedObject];
作为
self.userservice = [[self someMethodThatReturnsAnAutoreleasedObject]retain];
因此,您必须释放它,否则您的手上有泄漏(0(开始)+ 1(分配)- 1(自动释放)+ 1(保留)= +1)。