0

獲取例外,我有一個包含兩個託管對象上下文的應用程序:需要幫助設置後臺管理的對象上下文。在FRC controllerDidChangeContent

@property (nonatomic, strong) NSManagedObjectContext *managedObjectContext; 
@property (nonatomic, strong) NSManagedObjectContext *backgroundContext; 

我的一個視圖控制器是一個UITableView控制器響應NSFetchedResultsControllerDelegate。當我從遠程Web服務中獲取對象時,我想要在後臺線程上處理數據,將更改合併到我的主managedObjectContext並更新UI。

使用我當前的設置,當我嘗試獲取新對象時,出現以下異常。

CoreData: error: Serious application error. An exception was caught from the delegate of NSFetchedResultsController during a call to -controllerDidChangeContent:. *** -[__NSArrayM insertObject:atIndex:]: object cannot be nil with userInfo (null) 

此異常被提出在:

- (void)controllerDidChangeContent:(NSFetchedResultsController *)controller { 

    [self.tableView endUpdates]; 

} 

我的管理對象上下文中叫做AppController一個單獨的類創建。它目前看起來像這樣:

- (id)init {  
    self = [super init]; 
    if (self) { 
     sharedInstance = self; 

     // Registers NSManagedObjectContextDidSaveNotification 
     [[NSNotificationCenter defaultCenter] addObserver:self selector:@selector(mergeChanges:) name:NSManagedObjectContextDidSaveNotification object:self.managedObjectContext]; 

    } 

    return self; 
} 

- (void)mergeChanges:(NSNotification *)notification { 

    //should tell the main thread moc to run on the main thread, and merge in the changes there 
    [self.managedObjectContext performSelectorOnMainThread:@selector(mergeChangesFromContextDidSaveNotification:) withObject:notification waitUntilDone:YES]; 

} 


- (void)saveContext {  
    NSError *childError = nil; 
    [self.backgroundContext save:&childError]; 

    [self.managedObjectContext performBlock:^{ 
     NSError *parentError = nil; 
     [self.managedObjectContext save:&parentError]; 
    }]; 
} 


// Returns the managed object context for the application. 
// If the context doesn't already exist, it is created and bound to the persistent store coordinator for the application. 
- (NSManagedObjectContext *)managedObjectContext { 
    if (_managedObjectContext != nil) { 
     return _managedObjectContext; 
    } 

    NSPersistentStoreCoordinator *coordinator = [self persistentStoreCoordinator]; 
    if (coordinator != nil) { 
     _managedObjectContext = [[NSManagedObjectContext alloc] initWithConcurrencyType:NSMainQueueConcurrencyType]; 
     [_managedObjectContext setPersistentStoreCoordinator:coordinator]; 
     self.backgroundContext = [[NSManagedObjectContext alloc] initWithConcurrencyType: NSPrivateQueueConcurrencyType]; 
     self.backgroundContext.parentContext = self.managedObjectContext; 
    } 
    return _managedObjectContext; 
} 

任何想法,我失蹤或做錯了什麼?

回答

1

我認爲你必須在你的backround過程中創建你的backgroundContext。

,你需要聽由backgroundContext發出的通知:

[[NSNotificationCenter defaultCenter] addObserver:self selector:@selector(mergeChanges:) name:NSManagedObjectContextDidSaveNotification object:self.backgroundContext]; 
在我的情況runupdate

在後臺進程運行:

- (void) runUpdate { 
    NSManagedObjectContext *managedContext = [[NSManagedObjectContext alloc] init]; 
    managedContext.persistentStoreCoordinator = ...; 
    [updateController registerBackgroundMoc:managedContext]; 
    //do all update stuff 
    NSError *error; 
    if (![managedContext save: &error] { 
     ... 
    } 
    [updateController unregisterBackgroundMoc:managedContext]; 
} 
在我updateController

我做了以下內容:

- (void) registerBackgroundMoc: (NSManagedObjectContext *) updateMoc { 
    [[NSNotificationCenter defaultCenter] addObserver: self selector: @selector(mergeChanges:) name: NSManagedObjectContextDidSaveNotification object: updateMoc]; 
} 

- (void) unregisterBackgroundMoc: (NSManagedObjectContext *) updateMoc { 
    [[NSNotificationCenter defaultCenter] removeObserver: self name: NSManagedObjectContextDidSaveNotification object: updateMoc]; 
}