2011-11-08 52 views
1

我知道我的问题已经在StackOverflow上讨论过了,但我发现答案没有完成我的需求。所以,问题是:复制对象时的内存管理

NSMutableArray *firstArray = [[NSMutableArray alloc] initWithObjects: obj1,obj2,nil]; 
NSMutableArray *secondArray = [[NSMutableArray alloc] init]; 
secondArray = [firstArray mutableCopy]; 

什么是现在保留计数为secondArray? 2或1?我应该释放它两次还是一次? 复制或mutableCopy增加COPYING(此事件中的secondArray)对象的保留计数?

回答

5

你绝不应该关心绝对保留数。只有你是“平衡的”,这意味着每allocnew*,copy,mutableCopyretain你需要一个相应的releaseautorelease(当不使用ARC时,就是这样)。

如果将此规则应用于每行,您可以看到第二行有一个alloc,但没有发布。事实上,在这里分配一个实例是毫无用处的,因为无论如何你都不感兴趣。因此,它应该仅仅是阅读:

NSMutableArray *firstArray = [[NSMutableArray alloc] initWithObjects: obj1,obj2,nil]; 
NSMutableArray *secondArray = [firstArray mutableCopy]; 
// There is no third line. 

但是,让我们讨论您的原代码,看看发生了什么:

NSMutableArray *firstArray = [[NSMutableArray alloc] initWithObjects: obj1,obj2,nil]; 
NSMutableArray *secondArray = [[NSMutableArray alloc] init]; 
// secondArray points to a new instance of type NSMutableArray 
secondArray = [firstArray mutableCopy]; 
// You have copied another array (created a new NSMutableArray 
// instance) and have overwritten the pointer to the old array. 
// This means that the instance allocated in line 2 is still there 
// (was not released) but you don't have a pointer to it any more. 
// The array from line 2 has been leaked. 

在Objective-C,我们经常讲所有权的:有极少数中的方法使你成为一个对象的“所有者”。它们是:

  • alloc
  • new*,在newFoo
  • copymutableCopy
  • retain

如果调用这些,你会得到你的负责对象。这意味着您需要在这些对象上调用相应数量的release和/或autorelease。例如,如果你做[[obj retain] retain];然后[[obj autorelease] release];

+0

我想补充说,你有两个对象是拥有的,需要在某个阶段发布。你是对的 - 'retainCount'是unimporant - 只担心平衡拥有呼叫与释放呼叫。 – Abizern

+0

其实secondArray已被分配和使用在代码中的很远的地方。为了方便,我在第二行写了它。所以,如果我为了避免内存泄漏而正确解决了问题,我应该先释放secondArray,这将是绝对有效的? –

+0

@AndreyChernukha:完成后只能释放由'secondArray'指向的对象。释放意味着:*从这一行开始,我不再需要这个对象;它可能会被释放。*'autorelease'意味着:*很快,我不再需要它了;但至少在我离开这个方法之前它应该保持活跃状态​​。*(这不是100%正确,但足够接近事实是有用的) – DarkDust

1
NSMutableArray *firstArray = [[NSMutableArray alloc] initWithObjects: obj1,obj2,nil]; 
NSMutableArray *secondArray = [[NSMutableArray alloc] init]; 
secondArray = [firstArray mutableCopy]; 

正在发生的事情是,你已经创建了一个内存泄漏是罚款。当你用这行代码的firstArray的mutableCopy覆盖它时,你丢失了分配给secondArray的引用。

secondArray = [firstArray mutableCopy]; 

如果再放开secondArray两次,程序会崩溃,因为你那么overreleasing通过

secondArray = [firstArray mutableCopy]; 

你需要做的是分配可变数组,以确保你没有覆盖错误地保留了引用,并且平衡保留了发布。