例如,请查看以下示例:
代码1
-(NSString*)getString{
return [[[NSString alloc] initWithFormat:@"test"] autorelease];
}
-(void)printTestString{
NSString *testStr = self.getString;
[testStr retain]
NSLog(@"%@",testStr);
[testStr release]
}
代码2
-(NSString*)getString{
return [[NSString alloc] initWithFormat:@"test"];
}
-(void)printTestString{
NSString *testStr = self.getString;
NSLog(@"%@",testStr);
[testStr release];
}
代码1和代码2应该是有效的代码片段,不应出现泄漏。
代码1使用autorelease,因此返回变量必须保留在printTestString中并在使用后释放。因此,由于自动释放,这里有一个小的开销。
代码2不会在getString中释放NSString,因此您必须在使用它之后才释放它。似乎你必须少写,你没有开销,因为没有使用自动释放。
哪一种是事实上的“标准”方法?
我问自己的另一件事。可以在getString中自动释放并使用
保留[testStr retain]
是一个问题,当autorelease池在
之后立即释放变量时NSString *testStr = self.getString;
然后字符串就会消失。这是可能的还是编译器会阻止那种事情?
由于
-Sebo
答案 0 :(得分:2)
这样做:
-(NSString*)getString{
return [[[NSString alloc] initWithFormat:@"test"] autorelease];
}
-(void)printTestString{
NSString *testStr = self.getString;
NSLog(@"%@",testStr);
}
您的getString方法自动释放NSString,这意味着printTestString不需要保留或释放它。 getString中的自动释放是有意义的,因为它分配了对象,因此是对象的“所有者”。我建议在继续之前研究Objective-C的内存管理规则,因为它们非常重要。
答案 1 :(得分:2)
Jake的答案对于从方法返回对象所需的几乎所有情况都是正确的,但在某些情况下,您可能希望返回未自动释放的内容。从Memory Management Programming Guide(Mac版本,但它们是相同的规则):
如果您拥有对象的所有权 使用名称为的方法创建它 以“alloc”或“new”开头 包含“复制”(例如,alloc, newObject,或mutableCopy),或者如果你 发送保留信息。
另外,来自Coding Guidelines for Cocoa:
在你的方法和功能中 返回对象值,确保 你自动释放这些值 除非他们是对象创造或 对象复制方法(new,alloc,copy 和他们的变种)。 “自动释放” 这种背景并不一定意味着 对象必须是明确的 自动释放 - 即发送 以前自动释放到对象 归还它。从一般意义上说,它 只是意味着返回值不是 被来电者释放。
出于性能原因,它是 建议避免自动释放 方法实现中的对象 你可以,特别是代码 可能经常执行 在短期内;一个例子 这样的代码将是一个未知的循环 并且可能有很高的循环次数。
因此,包含前缀alloc
或new
的方法,或按惯例包含单词copy
的方法将让您返回未自动释放的对象。事实上,Clang Static Analyzer了解这个约定,并假设从遵循这些命名规则的方法返回非自动释放的对象。
在我不希望返回自动释放的对象(我不想管理自动释放池的紧密循环等)的情况下,我使用了new
前缀。同样,几乎在所有情况下都会推荐返回自动释放的对象,但有时您可能希望避免这种情况。