复制对象时的内存管理

发布于 2024-12-14 09:28:37 字数 385 浏览 4 评论 0原文

我知道我的问题已经在 StackOverflow 上讨论过,但我发现答案不完整,无法满足我的需求。所以问题是:

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

现在第二个数组的保留计数是多少? 2还是1?我应该释放它两次还是只释放一次? copy 或 mutableCopy 是否会增加 COPYING(此事件中的 secondaryArray)对象的保留计数?

I know that my question has already been discussed on StackOverflow but i found the answer not complete for my needs. So the question is:

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

what is retain count for the secondArray now? 2 or 1? Should i release it twice or just once?
Does copy or mutableCopy increases retain count of the COPYING (secondArray in this event) object?

如果你对这篇内容有疑问,欢迎到本站社区发帖提问 参与讨论,获取更多帮助,或者扫码二维码加入 Web 技术交流群。

扫码二维码加入Web技术交流群

发布评论

需要 登录 才能够评论, 你可以免费 注册 一个本站的账号。

评论(2

电影里的梦 2024-12-21 09:28:37

您永远不应该关心绝对保留计数。只是你是“平衡的”,这意味着对于每个 allocnew*copymutableCopyretain您需要相应的releaseautorelease(即不使用ARC时)。

如果将此规则应用于每一行,您可以看到第二行有一个分配,但没有释放。事实上,在这里分配一个实例是绝对没有用的,因为无论如何你对它都不感兴趣。所以它应该简单地读为:

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 keep] keep]; 然后 [[obj autorelease] release]; 就可以了

You should never care about the absolute retain count. Only that you're "balanced", that means for every alloc, new*, copy, mutableCopy and retain you need a corresponding release or autorelease (when not using ARC, that is).

If you apply this rule to each line you can see that your second line has an alloc, but there's no release. In fact, it's absolutely useless to allocate an instance here since you're not interested in it anyway. So it should simply read:

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

But let's discuss your original code and see what happened:

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.

In Objective-C, we often speak of ownership: there are very few methods that make you the "owner" of an object. These are:

  • alloc
  • new*, as in newFoo
  • copy and mutableCopy
  • retain

If you call these, you get an object for which you are responsible. And that means you need to call a corresponding number of release and/or autorelease on these objects. For example, you're fine if you do [[obj retain] retain]; and then [[obj autorelease] release];

月寒剑心 2024-12-21 09:28:37
NSMutableArray *firstArray = [[NSMutableArray alloc] initWithObjects: obj1,obj2,nil];
NSMutableArray *secondArray = [[NSMutableArray alloc] init];
secondArray = [firstArray mutableCopy];

发生的情况是您造成了内存泄漏。当您使用此行的firstArray 的mutableCopy 覆盖它时,您刚刚丢失了分配给secondArray 的引用。

secondArray = [firstArray mutableCopy];

如果您随后释放 secondaryArray 两次,程序将崩溃,因为您过度释放了由 分配的可变数组。

secondArray = [firstArray mutableCopy];

您需要做的是确保您没有错误地覆盖保留的引用,并且平衡保留与释放。

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

What is happening is that you've created a memory leak. You just lost the reference assigned to secondArray when you overwrote it with the mutableCopy of firstArray with this line.

secondArray = [firstArray mutableCopy];

If you then release secondArray twice, the program will crash because you're then overreleasing the mutable array assigned by

secondArray = [firstArray mutableCopy];

What you need to do is to make sure you're not overwriting retained references by mistake, and balance retains with releases.

~没有更多了~
我们使用 Cookies 和其他技术来定制您的体验包括您的登录状态等。通过阅读我们的 隐私政策 了解更多相关信息。 单击 接受 或继续使用网站,即表示您同意使用 Cookies 和您的相关数据。
原文