什么时候释放对象合适?

发布于 2024-10-14 22:16:37 字数 154 浏览 5 评论 0原文

我对此还是有点困惑。

我正在 Xcode 中以编程方式创建一个对象,比如说 UILabel,它也将是一个类范围的属性。

什么时候是释放对象的合适时间,是在创建对象的方法中,还是像普通 IBOutlet 对象一样在 dealloc 方法中?

谢谢。

I'm still a little confused on this.

I'm creating an object programmatically in Xcode, let's say a UILabel, which is also going to be a class wide property.

When is the proper time to release the object, in the method in which it is created, or in the dealloc method like normal IBOutlet objects?

Thanks.

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

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

发布评论

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

评论(2

夜访吸血鬼 2024-10-21 22:16:37

这取决于您的财产是否设置为保留价值。通常,您希望访问器(由 @synthesize 生成)在属性设置为新值时处理保留/释放。您指定这样的属性:

MyController.h

@interface MyController : UIViewController {
 UILabel *myLabel;
}

@property (nonatomic, retain) UILabel *myLabel;

@end

然后您可以使用 @synthesize 生成默认的 getter 和 setter。 “保留”属性的默认设置器将释放当前值并保留新值。但是,dealloc 中不会为您执行任何操作。这意味着,当控制器被销毁时,您对标签的引用将会泄漏,因为不会调用release。因此,您需要在 dealloc 中对所有“retain”属性调用release,如下所示:

MyController.m

@implementation MyController

@synthesize myLabel;

-(void) dealloc {
 self.myLabel = nil;

 [super dealloc];
}

@end

请注意,在这种情况下, self.myLabel = nil 几乎相当于调用 [myLabel release ] 因为 setter 将对现有值调用release,然后对新值调用retain。由于新值为 nil,因此调用 [nil keep] 无效。我更喜欢 nil 而不是release,因为你也将 ivar 设置为 nil 并避免悬空指针。

当您以编程方式(而不是通过 Interface Builder)创建这样的属性时,您不需要使用 IBOutlet 来标记它。在使用 IB 创建控件的情况下,您应该在 viewDidUnload 中清空所有 IBOutlet 引用。这是因为如果不保留您的控件,则它可能会与视图一起被释放。之后引用它会使应用程序崩溃,因此最好将它们置零,如下所示:

- (void)viewDidUnload {
    [super viewDidUnload];
    // Release any retained subviews of the main view.
    // e.g. self.myOutlet = nil;

    self.myIBLabel = nil;
}

使用属性时发生的另一个常见错误是省略“self”部分。如果您不使用 self.myIBLabel 表示法,则您将双通 getter 和 setter,并直接使用 ivar。这不会保留/释放该对象。

This depends on whether your property is set to retain the value or not. Usually you want the accessors (generated by @synthesize) to handle the retain/release when the property is set to a new value. You specify such a property like this:

MyController.h

@interface MyController : UIViewController {
 UILabel *myLabel;
}

@property (nonatomic, retain) UILabel *myLabel;

@end

You can then use @synthesize to generate the default getters and setters. The default setter for a 'retain' property will release the current value and retain the new value. However, nothing is done for you in dealloc. Meaning, that when the controller is destroyed, your reference to you label will leak since release will not be called. For this reason, you need call release on all your 'retain' properties in dealloc, like this:

MyController.m

@implementation MyController

@synthesize myLabel;

-(void) dealloc {
 self.myLabel = nil;

 [super dealloc];
}

@end

Notice that in this case, self.myLabel = nil is almost equivalent to calling [myLabel release] since the setter will call release on the existing value and then call retain on the new value. Since the new value is nil, calling [nil retain] has no effect. I prefer to nil instead of releasing since you are also setting the ivar to nil and avoids dangling pointers.

When you create a property like this programmatically as opposed to from Interface Builder, you don't need to mark it with IBOutlet. In the cases where you do create a control using IB, you should nil all of your IBOutlet references in viewDidUnload. This is because your control could be deallocated along with the view if it wasn't retained. Referencing it afterwards will crash the app so it's a good practice to nil them, like this:

- (void)viewDidUnload {
    [super viewDidUnload];
    // Release any retained subviews of the main view.
    // e.g. self.myOutlet = nil;

    self.myIBLabel = nil;
}

Another common mistake that happens when using properties is to omit the 'self' part. If you do not use the self.myIBLabel notation, you are bipassing the getter and setter and working with the ivar directly. This will NOT retain/release the object.

圈圈圆圆圈圈 2024-10-21 22:16:37

您应该在 dealloc 方法中释放它,尽管这取决于您创建类属性的方式。

如果您在创建它的方法中释放它,然后在类的其他部分中使用它(由于您正在使 UILabel 成为类范围的属性,我假设您是这样),那么您会得到一个糟糕的结果当您稍后尝试修改它时可以访问。请注意,如果您使用保留的属性,则需要考虑到这一点,在这种情况下,您可能会释放标签(因为您将创建它并将其分配给您的类属性,类属性将再次保留它)。

这是一个典型的例子:

- (void) someMethod {
    UILabel *myLabel = [[UILabel alloc] initWithFrame:myFrame];

    self.textLabel = myLabel;
    [myLabel release];
}


- (void) dealloc {
    [textLabel release];
}

You should release it in the dealloc method, although that depends how you're creating your class property.

If you release it in the method in which you create it, and then use it in some other part of your class (which, since you're making the UILabel a class wide property, I assume you are), you will get a bad access when you try to modify it later on. Note that if you're using a retained property you need to take that into account, in which case you might release the label (because you'll have created it and assigned it to your class property, which will retain it again).

Here's a typical example:

- (void) someMethod {
    UILabel *myLabel = [[UILabel alloc] initWithFrame:myFrame];

    self.textLabel = myLabel;
    [myLabel release];
}


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