obj-c NSString和alloc / retain / release

时间:2010-07-22 19:12:42

标签: objective-c nsstring release alloc

这可能是一个更多关于对象alloc / retain / release的问题,但我将以NSString为例。我知道我能做到:

NSString* myString = [[NSString alloc] initWithString:@"Test"];

基本上分配和初始化由我的变量myString引用的字符串,我稍后应该调用[myString release]。但是,如果在我这样做之后,我将其设置为其他字符串,例如:

myString = someOtherString;

这实际上是否会造成内存泄漏,因为我已经将指针重新分配给另一个对象而丢失了对我分配的原始引用的所有引用?

如果我只想亲自分配和释放字符串然后在不同时间更改其值,我应该使用除“=”之外的其他语法,还是重载以正确更改最初对象的内容当我使用=。时,由myString表示。

3 个答案:

答案 0 :(得分:4)

是的,在您的示例中,您正在泄漏内存。

NSString* myString = [[NSString alloc] initWithString:@"Test"];
myString = someOtherString;

你应该这样做:

NSString* myString = [[NSString alloc] initWithString:@"Test"];
[myString release];
myString = someOtherString;

我听到所描述的整个保留/释放事物的最佳方式是想象你正在为某人遛狗。你的“对象”是一只狗,“保留”将一条带子放在狗身上,“释放”带走了一条带子。您可以根据需要在狗身上放置尽可能多的牵引带,但是您想要在狗身上至少留一条皮带,这样他就不会自由跑(泄漏)而且你想把它带回狗身上的所有牵引带对所有者(你想摆脱对象)。在你的例子中,你可以把它想象成放开狗中途的皮带并捡起另一只狗的皮带。

答案 1 :(得分:1)

如果在为其分配另一个指针值之前正确地放弃了所有权,则没有泄漏:

NSString *a = [[NSString alloc] init];
// ... 
[a release]; // relinquish ownership
a = someOtherString; // fine, we don't own the previous instance anymore

当您通过调用release放弃对象的所有权时,您应该认为它已被有效解除分配 - 这可能是最后一次引用它。指针仍然具有相同的值只是实现和使用Objective-C类类型的副作用。

根据内存限制和代码的作用,您还可以使用autorelease d实例:

NSString *a = [NSString stringWithString:@"moo"];
a = someOtherString; // fine, a will be released later by the nearest autorelease pool

请注意,如果引用不是局部变量而是ivar,您可能希望改为使用declared properties

答案 2 :(得分:0)

您可以执行以下操作:

NSString *myString = [NSString stringWithString:@"Test"];

返回的字符串是自动释放的,因此您不必释放它。你也不“拥有”它。如果这是一个问题,就像其他人建议的那样,并在重新分配它的价值之前向release发送myString消息。