当我在层次结构中导航时,我在解除分配控制器时遇到问题。我发现问题出在于从Core Data加载的对象。当我使用// *
注释掉行时,控制器已成功取消分配,但如果行已就位,则不会打印NSLog
。
我从控制器中提取代码:
@implementation ModulesListViewController {
NSArray *_modules;
}
- (void)viewDidLoad {
[super viewDidLoad];
_modules = [[StorageManager manager] getModulesCDByUserEmail:userEmail]; // *
...
}
- (void)dealloc {
NSLog(@"ModulesListViewController dealloc");
}
getModulesCDByUserEmail
是从Core Data获取数据并返回NSArray
的方法。没什么不寻常的。我想问题出在NSManagedObjectContext
。
- (NSManagedObjectContext *)managedObjectContext{
if (_managedObjectContext != nil) {
return _managedObjectContext;
}
_managedObjectContext = [[NSManagedObjectContext alloc] initWithConcurrencyType:NSMainQueueConcurrencyType];
_managedObjectContext.parentContext = [self writerManagedObjectContext];
return _managedObjectContext;
}
我在单身中拥有它,并且它是全局可访问的,因此它不会被释放。这是一个问题吗?如果我想要正确解除分配,我应该为每个控制器创建自己的NSManagedObjectContext
吗?这些情境可能是NSMainQueueConcurrencyType
吗?或者有没有办法解除从未被释放的上下文中取出的对象?
感谢您的帮助
答案 0 :(得分:2)
NSManagedObjectContext
。没有价值。阵列未保留视图控制器,因此阵列不会导致保留问题。但是,使用该行代码注释掉您的_modules
变量nil
,这意味着针对该变量的其他活动会产生nil
响应。我建议通过视图控制器跟踪该变量,并找出导致保留循环的位置。它不在那行代码中。
另外,请考虑使用@property
而不是像这样的直接ivar。它将允许编译器进行更多优化,并让ARC更好地完成工作。
最后,如果这是您正在使用的表视图,请考虑使用NSFetchedResultsController
而不是您自己的数组。使用更少的代码,您将获得更好的性能。