到目前为止,我使用的是共享的Coredata实例。我在视图控制器中调用[[Storage instance] managedObjectContext]
在视图控制器中传递的位置!
你说我可能是完全错的?请告诉我原因。
我注意到在大多数示例中,viewControllers在头文件中的@private中都有managedObjectContexts。为什么我们需要私人电话?
最后我们声明像
NSManagedObjectContext *_managedObjectContext;
@property (nonatomic, strong) NSManagedObjectContext *managedObjectContext;
然后在viewController.m
@synthesize managedObjectContext = _managedObjectContext;
是什么意思“ _ ”managedObjectContext。为什么是下划线?
最后,这一切将如何影响iCloud?在一篇教程中,作者说,
ivars应该是私有的,所有代码都非常重要 总是通过访问器方法来确保这些 正确初始化。没有搞笑的 _ ,那么KVC可能会“帮助”我们 太多了。使用iCloud异步导入数据,还有更多 时间和多线程问题
没有搞笑的 _ ...请解释在这里发生的w ..
@interface LStorage : NSObject {
@private
NSString *identifier;
NSManagedObjectContext *managedObjectContext;
NSManagedObjectModel *managedObjectModel;
NSPersistentStoreCoordinator *persistentStoreCoordinator;
}
@property (nonatomic, retain, readonly) NSManagedObjectContext *managedObjectContext;
+ (LStorage *) instance;
in LStorage.m
+ (LStorage *) instance {
@synchronized(self) {
if (instance == nil) {
instance = [[LStorage alloc] initWithIdentifier:kIdentifier];
}
}
return instance;
}
//identifier is just used to name the mom model filename.
- (id) initWithIdentifier:(NSString *)anIdentifier {
self = [super init];
if(self != nil) {
identifier = anIdentifier;
}
return self;
}
- (NSManagedObjectContext *)managedObjectContext {
if (managedObjectContext != nil) {
return managedObjectContext;
}
NSPersistentStoreCoordinator *coordinator = [self persistentStoreCoordinator];
if (coordinator != nil) {
// Make life easier by adopting the new NSManagedObjectContext concurrency API
// the NSMainQueueConcurrencyType is good for interacting with views and controllers since
// they are all bound to the main thread anyway
if(IOS_VERSION_GREATER_THAN_OR_EQUAL_TO(@"5.0")){
NSManagedObjectContext* moc = [[NSManagedObjectContext alloc] initWithConcurrencyType:NSMainQueueConcurrencyType];
[moc performBlockAndWait:^{
// even the post initialization needs to be done within the Block
[moc setPersistentStoreCoordinator: coordinator];
[[NSNotificationCenter defaultCenter]addObserver:self selector:@selector(mergeChangesFrom_iCloud:) name:NSPersistentStoreDidImportUbiquitousContentChangesNotification object:coordinator];
}];
managedObjectContext = moc;
}else{
managedObjectContext = [[NSManagedObjectContext alloc] init];
[managedObjectContext setPersistentStoreCoordinator:coordinator];
}
}
return managedObjectContext;
}
答案 0 :(得分:0)
您没有展示NSManagedObjectContext的初始化方式,但我假设您使用的是Apple提供的样板代码。如果是这种情况,你应该有一个评估员:
- (NSManagedObjectContext*)managedObjectContext
{
if (_managedObjectContext != nil)
return _managedObjectContext;
// Code to initialise and return context here
}
请注意,managedObjectContext
在此方法中已延迟加载。这意味着只有在第一次通过self.managedObjectContext
或[self managedObjectContext]
访问方法时才会创建上下文(如果您可以从其他类访问该属性,则可以在外部创建)。
现在想象从未访问过此方法,因此您的_managedObjectContext
ivar指向nil或内存垃圾。如果您尝试直接访问ivar,则会因为该内存块中没有存储NSManagedObjectContext
而导致崩溃。
这也是通常在ivar名称的开头或结尾添加下划线(_)的原因,以避免您意外地直接访问ivar而不是通过其合成的getter。
如果ivar只是简单地命名为managedObjectContext
,那么犯错误就更容易了,即你可能只写self.managedObjectContext
而不是写managedObjectContext
,而你突然直接访问了ivar。
基本上synthesize managedObjectContext = _managedObjectContext;
的意思是 *合成一个名为managedObjectContext
的getter(可能是setter)方法,并将其分配给名为_managedObjectContext的ivar。*