【问题标题】:release view in viewDidUnload在 viewDidUnload 中释放视图
【发布时间】:2011-05-30 09:00:19
【问题描述】:

我知道如果我通过使用属性来保留 IBOutlet,那么我必须在 viewDidUnload 中将其设置为 nil,但其他人呢?

例如,我有三个子视图 view1、view2 和 view3,它们从 nib 加载,这是控制器的头文件

@interface MyViewController : UIViewController {
    IBOutlet UIView *view1;
    UIView *view2;
    //no reference for view3
}
@property (nonatomic, retain) IBOutlet UIView *view2;  //property view2 is an IBOutlet!!
@end

和方法viewDidUnload

- (void)viewDidUnload {
    self.view2 = nil;
    //[view1 release];
    //view1 = nil;
    [super viewDidUnload];
}

我必须释放 view1 并将其设置为 nil 吗?或者 UIViewController 会为我将它设置为 nil 吗? view3 呢?

我还必须在dealloc 中发布view1 吗?

编辑: 我想很多人不明白我的问题

首先,view1 是一个声明为 ivar 的 IBOutlet,分配 ivar 不会保留它。我知道 UIViewController 肯定会保留它,但我必须释放它还是 UIViewController 会为我释放它?如果 UIViewController 将释放它,那么我不必再次释放它。

其次,view2 也是一个 IBOutlet,尽管它被声明为属性而不是 ivar。

@property (nonatomic, retain) IBOutlet UIView *view2;

它是一个保留属性,因此设置它会保留它,所以我知道我必须将它设置为 nil 才能释放它。我没有问题。

对于 view3,没有任何参考,因此我假设我不必对此做任何事情。我还假设不需要在 nib 中引用 every 对象。

【问题讨论】:

  • 为什么没有view3的引用?
  • 不是答案,但如果您在理解引用计数时遇到问题,只需记录它们:NSLog(@"view1 retainCount: %d", [view1 retainCount])。这将帮助您查看要发布哪些视图。还可以使用“泄漏”工具(构建 -> 配置文件)。请记住,这并不总是能捕获泄漏,例如当您的 viewController 从未被释放时(因为从技术上讲,这不是问题 - 但它是更好的准备方式)。
  • @Deepak 我必须为 nib 中的每个子视图做一个参考吗?
  • @fzwo 我对理解从 nib 加载的视图的所有权有疑问,MyViewController 是否拥有该视图或其超类(UIViewController)拥有该视图?
  • @xlc0212 实际上,您的 ViewController 拥有它。您的 VC UIViewController - 仅具有增强的、更严格的定义。这就是子类化的概念。让我推荐一个very good book来学习iOS开发。这以一种易于理解的方式解释了最有趣的主题。请注意,这是一本学习书,因此请从头到尾进行操作。这将为您在以后的项目中节省大量时间和烦恼。

标签: cocoa-touch ios uiview uiviewcontroller


【解决方案1】:

默认情况下会保留所有出口,即使它们没有为它们声明属性。所以你需要释放它们。如果您继续将assigned 属性声明为插座,那么您不需要发布,但您也不能依赖它,因为您不是所有者。

因此,您需要同时释放 view1view2,因为它们被声明为网点。 view3 是一个不存在的变量,因此不必担心。

【讨论】:

  • view2 的出口提及在这里@property (nonatomic, retain) IBOutlet UIView *view2;
【解决方案2】:

加载 nib 时,它的所有对象都会自动实例化并保留。 您的 nib 文件的文件所有者就是您的 UIView 的所有者。

如果您使用 UIView *view2,则无法使用界面生成器连接它们。 所以这对我来说没有任何意义。

你也必须在 dealloc 中释放。

- (void)viewDidUnload {
  self.view1 = nil;
  self.view2 = nil;
  [super viewDidUnload];
}

- (void)dealloc {
  [self.view1 release];
  self.view1 = nil;
  [self.view2 release];
  self.view2 = nil;
}

【讨论】:

  • 我可以通过属性连接view2,属性将为我保留view2。对于您的dealloc 代码,为什么要释放然后设置为零?我认为这会导致崩溃,因为将属性设置为 nil 将再次释放,因为这是一个保留属性
猜你喜欢
  • 1970-01-01
  • 2011-01-22
  • 2011-11-18
  • 1970-01-01
  • 2011-03-12
  • 2011-07-26
  • 1970-01-01
  • 2011-04-05
  • 2011-03-14
相关资源
最近更新 更多