注意:这是由于一些 XCode beta 版本中的一个 bug 导致的,这个 bug 早已被修复。如果您对 ARC 有疑问,此问答可能对您没有帮助。
我正在将我的项目从手动引用计数迁移到 ARC,并且偶然发现了一个问题:如何确保保留属性的自定义设置器实际保留?
在myClass.h
中,我声明了一个属性:@property (retain) NSDate *date
。我是手动设置__strong
ivar 还是让它自动生成都没有关系。
在实现中,我当然有@synthesize date
,并实现了一个自定义设置器(或者只是下载演示 Xcode 项目):
- (void)setDate:(NSDate *)newDate
{
if (allowedToSetNewDate)
{
date = newDate;
}
}
这似乎没有保留日期,并message sent to deallocated instance
在 newName (自动)发布它来自的地方,myClass.date
稍后尝试访问时给我(假设 Zombie 已启用;否则,它只是默默地崩溃)。
更改要使用的设置器可以date = [newDate copy]
解决该错误,但这并不是我真正想要的。删除自定义设置器也可以,但显然是不可取的。
我在这里想念什么?如何确保保留属性的自定义设置器实际上保留在 ARC 环境中?这似乎是一项基本和常见的任务,我认为我忽略了一些非常明显的事情。
(注意:这不属于任何 Apple NDA 的条款,因为 ARC 作为 LLVM 的一部分公开发布)
编辑:我创建了一个小型 Xcode 项目来演示该问题并将其上传到 github。随意下载并玩。我已经束手无策了(尽管我的机智今天不是最好的,诚然)。
编辑:对于此示例项目,此问题已解决(请参阅接受的答案)。不幸的是,在我无法自由分享的更大项目中,问题仍然存在。作为一种解决方法,我添加strong
了带有合成设置器的重复属性(ivars 不起作用)。新的自定义设置器现在看起来像这样:
- (void)setDate:(NSDate *)newDate
{
if (allowedToSetNewDate)
{
self.date_arcretain = newDate; //this property is only there as a workaround. ARC properly retains it, but only if the setter is synthesized
date = newDate;
}
}