14

我对内存管理技术仍然不是很好,想知道是否有人可以向我解释这种奇怪的行为。考虑一下我一直在测试的这 3 段代码:

DofView* dofView = [[DofView alloc] initWithNibName:@"DofView" bundle:nil];
NSLog(@"dof retain count = %d", [dofView retainCount]); 

这记录:保留计数 = 1。这很好。

DofView* dofView = [[DofView alloc] initWithNibName:@"DofView" bundle:nil];
[dofView release];
NSLog(@"dof retain count = %d", [dofView retainCount]); 

这记录:保留计数= 1。不应该是0吗?

DofView* dofView = [[DofView alloc] initWithNibName:@"DofView" bundle:nil];
[self.navigationController pushViewController:dofView animated:YES];
NSLog(@"dof retian count = %d", [dofView retainCount]);

此日志:保留计数 = 5。我不知道为什么它是 5?

任何人都可以对此有所了解吗?我担心每次创建新视图时都会占用内存。

谢谢!

4

7 回答 7

2

不要依赖于retainCount内存分析。浏览有关内存管理的参考文档以获取更多信息

于 2011-05-10T11:30:41.767 回答
2

强烈建议不要查看保留计数,它不会为您提供任何有价值的信息。如果你想知道某些东西是否被正确释放,你应该在你的类的 dealloc 方法中放置一个断点或一个日志条目——当调用 dealloc 时,该对象很快就会被释放。除了工具应用程序,这是我用来查找保留周期的工具。

于 2011-05-10T11:35:00.847 回答
1

何时使用 -retainCount?

保留计数似乎没用

于 2011-05-10T11:31:54.963 回答
1

知道释放立即发生很重要(自动释放需要一段时间)。

那么为什么您的对象的保留计数仍然为 1?

因为它已经被释放了——它不再是你的对象了,它只是一些空闲的内存!

尝试这样做:

NSObject* o = [[NSObject alloc] init];
NSLog(@"retain count = %d", [o retainCount]); 
[o retain];
NSLog(@"retain count = %d", [o retainCount]); 
[o release];
NSLog(@"retain count = %d", [o retainCount]); 
[o release];
NSLog(@"retain count = %d", [o retainCount]); 

你得到输出

retain count = 1
retain count = 2
retain count = 1
retain count = 1

您可能希望最后一行显示 0,而不是 1。但是,如果要释放它,它不会减少保留计数 - 这有什么意义!

实际上,最后一行输出任何东西而没有崩溃的事实是幸运的——因为对象已被释放,没有什么能阻止内存被其他东西使用——它现在实际上只是随机数据。这正是导致 EXC_BAD_ACCESS 崩溃的那种错误 :)

实际上,您会在最终结果中收到编译器分析器警告,NSLog因为您将消息传递给不再存在的对象:)


至于 5 的保留计数-我只能回应其他答案-您不知道对象内部发生了什么-仅仅因为您只调用了一次保留并不意味着没有其他人调用保留 :)

只要你释放你所做的每一个保留,你就做对了。

如果您担心泄漏,请使用分析器并检查!

于 2011-05-10T11:43:25.017 回答
0

retainCount 属性取决于 UINavigationController 如何处理您正在推送的控制器。如果它在 UIViewController 对象中多次保留,您不必担心。重要的是,当使用该对象时,您将在不再需要它时释放它。

例如,在这种情况下,由于您将新控制器推送到导航器,您应该这样做:

DofView* dofView = [[DofView alloc] initWithNibName:@"DofView" bundle:nil];
[self.navigationController pushViewController:dofView animated:YES];
[dofView release];

对象的保留计数可能不会立即更新,因此您不应该真正关心该计数。

如果你认为你正在泄漏内存,你应该使用 Xcode 中的分析工具(搜索内存泄漏)。

希望这可以帮助。

于 2011-05-10T11:32:15.183 回答
0

不要依赖保留计数。过去,我也尝试检查内存管理的保留计数,但它总是让我感到困惑(当保留计数让我感到困惑时,请查看此链接 [http://stackoverflow.com/q/5483357/644149]。只需遵循简单的指南,然后你会您的应用程序中没有内存泄漏

当你使用 alloc、new、copy、retain 时,你也应该释放那个对象。简单的

于 2011-05-10T11:47:54.463 回答
-1

release调用不会立即生效,因此保留计数可能看起来不正确。您可以使用 Leaks 工具来跟踪内存问题,但只要您遵循内存管理规则,通常应该没问题。

于 2011-05-10T11:28:48.780 回答