2012-04-03 49 views
11

使用帶有NSPrivateQueueConcurrencyType有必要做任何觸及,或屬於其內performBlock:performBlockAndWait:當使用NSMainQueueConcurrencyType時,是否有必要在performBlock中執行Core Data讀取?

對象是對NSMainQueueConcurrencyType同一真正的被管理對象的情況下,當據丹尼爾埃蓋特在this question答案嗎?試想一下,在主線程中運行下面的代碼,在一個UIViewController例如:

self.moc = [[[NSManagedObjectContext alloc] initWithConcurrencyType:NSMainQueueConcurrencyType] autorelease]; 
//moc setup 

__block RHWidget *widget = nil; 

[self.moc performBlockAndWait:^{ 
    widget = [(RHWidget *)[self.moc objectWithID:self.widgetObjectID] retain]; 
}]; 

self.labelView.text = widget.descriptionString; 

[widget release]; 

是否可以安全使用插件的外塊,因爲我們知道我們是在主線程?或者,它是有必要做到這一點:

__block NSString *description = nil; 

[self.moc performBlockAndWait:^{ 
    RHWidget *widget = (RHWidget *)[self.moc objectWithID:self.widgetObjectID]; 
    description = [widget.descriptionString copy]; 
}]; 

self.labelView.text = description; 

[description release]; 

做的事情改變,如果有另一個NSManagedObjectContext在那裏,可能是私有隊列式的,以塊做的工作,推動變化高達self.moc作爲parentContext

當然這是一個稍微有點人爲的例子,但是安全地將該小部件傳遞給例如需要訪問部件的某些屬性的模式視圖控制器會很好。我應該傳遞小部件的objectID,並在新視圖控制器中的performBlock:內重新設定它?

+0

有一篇非常全面的文章[這裏](http://www.cocoanetics.com/2012/07/multi-context-coredata/),它描述了各種方法,包括上下文併發類型和嵌套上下文。 – 2012-09-22 20:40:57

回答

6

更新:根據WWDC 2011 Session 303 (What's New in Core Data on iOS),NSMainQueueConcurrencyType旨在允許在主線程上的正常消息;與其他線程的上下文進行交互時,只需使用-performBlock:。 (我下面原來的答案的還是相關的部分。)


我做了修改Xcode的默認的「主從」應用程序模板,使「主」 MOC一個應用程序或兩個(由創建的應用程序委託並在視圖控制器之間傳遞)僅限於主隊列,父對象用於後臺操作(如從Web抓取導入數據)使用的私有隊列上下文。因此,上下文及其對象的大部分使用都不會被包裹在performBlock:中。 (我使用performBlock:的唯一時間是將更改從後臺任務上下文推回到主更新UI。)工作得很好。

+0

這或多或少是我在做的;我有一個帶有「NSOperationQueue」的單例和一個帶有「NSPrivateQueueConcurrencyType」的上下文,它傳遞給每個操作。這些操作獲取對象,完成它們的工作,保存本地上下文,然後保存父上下文,所有操作都在'performBlock:'內。一切似乎都行得通,但我擔心一個無法預料的競爭條件或內存管理問題。 – roland 2012-04-03 16:28:30

+0

@roland。我不認爲這是一種安全的方法,因爲NSOperationQueue可以使用多個線程(即使其maxConcurrentOperationCount爲1)。當您使用父/子上下文mecanism時,您的併發性問題會更少,因爲它始終是訪問存儲的父上下文。 – FKDev 2012-05-03 19:24:51

相關問題