2013-08-02 25 views
1

如何爲已創建的UIManagedDocument創建managedObjectContext並將其與全局調度隊列相關聯?或者什麼是創建managedObjectContext的正確方法。爲已創建的UIManagedDocument創建後臺隊列的managedObjectContext

信息:我一起對付我managedObjectContext在最原始的辦法,只是通過創造它與managedDocument _managedDocument = [[UIManagedDocument alloc] initWithFileURL:url];

然而,這將與主隊列,這是我想避免managedObjectContext相關聯,並將其與此隊列相關聯。

_backgroundQueue = dispatch_get_global_queue(DISPATCH_QUEUE_PRIORITY_BACKGROUND, 0); 

這樣做的正確方法是什麼?

回答

2

好了,解決了這個問題,確切的答案:

核心數據要求每個隊列經營着自己的獨立managedObjectContext,這是在隊列中,它會創建屬於。當數據在managedObjectContext上被提取時,它將被合併到主隊列的管理對象上下文中。要創建背景managedObjectContext,請爲其提供與主隊列的managedObjectContext相同的持久存儲協調器。使用此通知,當後臺管理對象上下文保存時,更改將發送到主隊列併合並。

然後執行提取的好方法是在performBlock:內部執行,以確保您在右側進行提取隊列。

[_backgroundManagedObjectContext performBlock:^{ 
     // fetch here 
    }]; 

完整列表:

@implementation databaseManager { 
    UIManagedDocument* _databaseManagedDocument; 

    NSManagedObjectContext* _backgroundManagedObjectContext; 
    dispatch_queue_t _backgroundContentFetchingQueue; 

} 

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

     NSURL* url = [[[NSFileManager defaultManager] URLsForDirectory:NSDocumentDirectory inDomains:NSUserDomainMask] lastObject]; 
     url = [url URLByAppendingPathComponent:@"database"]; 

     _databaseManagedDocument = [[UIManagedDocument alloc] initWithFileURL:url]; 
     _backgroundContentFetchingQueue = dispatch_get_global_queue(DISPATCH_QUEUE_PRIORITY_BACKGROUND, 0); 

     [self openManagedDocument]; 
    } 

    return self; 
} 

- (void)initializeBackgroundManagedObjectContext 
{ 
    dispatch_async(_backgroundContentFetchingQueue, ^{ 

     NSPersistentStoreCoordinator *coordinator = _databaseManagedDocument.managedObjectContext.persistentStoreCoordinator; 
     if (!coordinator) { 
      // Error if we don't have a coordinator. 
      return; 
     } 

     // Create the Background Managed Object Context 
     _backgroundManagedObjectContext = [[NSManagedObjectContext alloc] initWithConcurrencyType:NSPrivateQueueConcurrencyType]; 
     [_backgroundManagedObjectContext setPersistentStoreCoordinator:coordinator]; 
     [_backgroundManagedObjectContext setUndoManager:nil]; 

     // Notify the main queue of changes the background queue makes 
     [[NSNotificationCenter defaultCenter] addObserverForName:NSManagedObjectContextDidSaveNotification 
                  object:_backgroundManagedObjectContext 
                  queue:[NSOperationQueue mainQueue] usingBlock:^(NSNotification *note) { 
                   dispatch_async(dispatch_get_main_queue(), ^{ 
                    [_databaseManagedDocument.managedObjectContext mergeChangesFromContextDidSaveNotification:note]; 
                   }); 
                  }]; 
    }); 

} 

- (void)openManagedDocument 
{ 
    if (!([[NSFileManager defaultManager] fileExistsAtPath:[_databaseManagedDocument.fileURL path]])){ 
     [_databaseManagedDocument saveToURL:_databaseManagedDocument.fileURL forSaveOperation:UIDocumentSaveForCreating completionHandler:^(BOOL success){ 
      if (success) { 
       [self initializeBackgroundManagedObjectContext]; 
      } else NSLog(@"Database document creation error"); 
     }]; 
    } else if (_databaseManagedDocument.documentState == UIDocumentStateClosed) { 
     [_databaseManagedDocument openWithCompletionHandler:^(BOOL success){ 
      if (success) { 
       [self initializeBackgroundManagedObjectContext]; 
      } else NSLog(@"Database document opening error"); 
     }]; 

    } else if (_databaseManagedDocument.documentState == UIDocumentStateNormal) { 

     [self initializeBackgroundManagedObjectContext]; 
    } 
} 

- (void)dealloc 
{ 
    dispatch_release(_backgroundContentFetchingQueue); 
} 

@end 

希望我沒有錯過任何東西。原帖在這裏:POST