【发布时间】:2013-08-06 20:54:56
【问题描述】:
想象三个班级。 ClassA 和 ClassB 是我的。第三类是 UIViewController,我不能修改它的代码:
在A类中:
- (void) aMethod
{
ClassB *classBInstance = [[[ClassB alloc] init] goWithOptions:options];
}
ClassBInstance 仅在 aMethod 的生命周期内保留。
在 B 类中:
- (void) goWithOptions
{
AUIViewController *avcInstance = [[AUIViewController alloc] init];
avcInstance.delegate = self;
[viewController pushViewController:avcInstance animated: YES]; // this returns immediately, but we need self to be retained until the delegate is done with it
}
- (void) cleanupCalledByDelegate //
{
// cleanup
}
当-goWithOptions方法被调用时,avcInstance被被调用者保留,但是传递给delegate的self却没有。这意味着只要-goWithOptions 返回,并且aMethod 完成,那么classBInstance 就会被释放,而avcInstance 的delegate 将不再有效。
理想情况下,我想将classBInstance(属于B 类的自己)的所有权绑定到avcInstance;当avcInstance 被释放时,classBInstance 或委托被释放。
或者,我可以在 -cleanupCalledByDelegate 中清理 classBInstance,它在 avcInstance 被释放之前调用。
如何最好地处理这个问题?我宁愿不让ClassB *classBInstance 成为ClassA 的属性,因为那样我就必须让它释放classBInstance,我更愿意在ClassB 中处理它。如果这是最好的解决方案,我会使用块并在 ClassA 中传递一个完成块:
{
classBInstance = nil;
}
到-goWithOptions,我会打电话给-cleanupCalledByDelegate。这是处理这个问题的正确方法吗?
【问题讨论】:
-
arc 的一个缺点是你没有太多的控制权。保留/释放现在与属性相关联。要保留/释放某些内容,您必须添加另一个属性。
-
@JustinMeiners - 不仅仅是属性。强大的 ivars 也适用于范围和关联。
-
@TomSwift 对,关键是,它现在绑定到一个命名变量,使得解决这类问题变得更加麻烦。
标签: ios objective-c delegates automatic-ref-counting