我们有一个具有相当广泛的核心数据模型的应用程序,在Objective C中实现了许多自定义子类,但是在Swift中编写的应用程序中也越来越多地使用了这些子类。 (对于它的价值:我们使用Xcode 7.3.1针对iOS 9.3进行构建,因此Swift代码为2.2。)
有一个用Swift编写的辅助函数,如下所示:
extension NSManagedObject {
func inContext<T: NSManagedObject>(moc: NSManagedObjectContext) -> T? {
guard self.managedObjectContext != moc else {
return (self as! T)
}
do {
let obj = try moc.existingObjectWithID(self.objectID)
return (obj as! T) // <--- fails here
}
catch let error {
return nil
}
}
}
在相当多的对象跳转上下文的地方调用它。调用代码通常如下所示:
let result: ECFoo? = foo.inContext(managedObjectContext)
这在应用程序的调试版本中完美运行。但是在启用优化的情况下,我遇到了这样的调用在我标记的行中失败的情况,其中所获取的对象从NSManagedObject
转换为正确的子类。堆栈跟踪以swift_dynamicCastObjCClassUnconditional
开头,并且记录到控制台的消息是:
无法转换类型&#39; ECFoo_Foo _&#39; (0x7fb857d2c250)到&#39; ECFoo_Foo _&#39; (0x7fb857d2c250)。
如果我在该行上设置断点,我在调试器控制台中尝试做的事情似乎很好:
(lldb) po moc.existingObjectWithID(self.objectID)是ECFoo
真
这非常令人困惑,因为它在这里明显是同一类型,它们似乎都是动态生成的子类,而不是它应该尝试转换为的正式类(基于调用代码的推断)。我只能假设有一些信息被优化掉,这是完成这项工作所必需的,但我并不完全确定如何修复它。