2012-08-22 48 views
3

我有一堆服務器請求,我可以異步運行,但我需要等待他們都完成之前,我繼續。試圖等待一組NSURLConnections來完成

dispatch_group_async它似乎很合理,但我不能得到它的工作。它要麼永遠封鎖,要麼根本不封鎖。我的最新嘗試,看起來像....

dispatch_group_t group; 

- (void)cleanRoom { 
    NSAssert(![NSThread isMainThread], @"not on main thread."); 
    group = dispatch_group_create(); 

    for (Junk *thing in myRoom) { 
    // take it off the current thread 
     dispatch_async(dispatch_get_global_queue(DISPATCH_QUEUE_PRIORITY_DEFAULT, 0), ^{ 
      // register code against group 
      dispatch_group_enter(attachmentGroup); 
      NSURLConnectionWrapper *wrapper = [[NSURLConnectionWrapper alloc] init]; 
      wrapper.delegate = self; 
      [wrapper sendRequestFor:thing]; 
     }]; 
    } 

    // wait till the stuff is the group is done 
    dispatch_group_wait(attachmentGroup, DISPATCH_TIME_FOREVER); 
    NSLog(@"waiting complete!!!!"); 

    // process the results now that I have them all 
} 

- (void)wrapperConnectionDone { 
    // do a bit more junk 
    dispatch_group_leave(group); 
} 

這將導致它永遠阻塞,因爲NSURLConnectionDelegateNSURLConnectionDataDelegate方法永遠不會獲取調用。我假設我已經以某種方式阻止他們的線程,但使用NSLog我可以確認NSURLConnection是在與我的cleanRoom方法不同的線程。

我讀了一些關於沒有運行循環來做回調的其他線程,所以我嘗試了像connection setDelegateQueue:[NSOperationQueue mainQueue]][[NSRunLoop currentRunLoop] runUntilDate:[NSDate distantFuture]]之類的東西,但是沒有什麼不明顯的效果。

+ sendAsynchronousRequest:queue:completionHandler:不適合我,我有一些醜陋的認證。我已經看到了一些很好的例子,但我沒有適應。

我很明顯缺少一些基本位,但我找不到它。

+1

我一直在使用NSOperations來做到這一點,當隊列變爲0時,你知道你已經完成了。簡單易用的代碼 - 一個操作管理器和一個NSOperation示例子類,可以在這裏找到:github.com/dhoerl/NSOperation-WebFetches-MadeEasy。在OperationsRunner.h中有一個「如何做」。也就是說github上有很多這樣的操作。 –

+0

你有一個很好的觀點。早些時候,我在'NSURLConnection'上使用'setDelegateQueue:[NSOperationQueue mainQueue]]'來代替更多的簡化代碼,而不是在調用代碼中創建額外的GCD塊。現在我已經開始使用GCD,我可能會返回並將其切換回來以方便閱讀。在很多情況下,NSOperation和GCD可以用來做同樣的事情。對於其他誰可能遵循,http://stackoverflow.com/questions/10373331/nsoperation-vs-grand-central-dispatch是相當描述。 – DBD

回答

2

NSURLConnection需要在具有處理後的運行循環的線程上運行。最簡單的這樣的線程是主線程。所以只需dispatch_async這些連接創建到dispatch_get_main_queue()和其餘的dispatch_group邏輯應該沒問題。請記住,委託方法將主線程(從NSURLConnection概述)上被稱爲:

這些委託方法被稱爲啓動該異步加載操作相關的NSURLConnection的對象的線程上。

+0

太棒了,它的工作。事實證明這是一個複雜的問題。我在另一個進程中不知不覺地阻塞了我的主線程,所以即使我在運行循環中將它們放在主線程上,也不會進行NSURLConnectionDelegate調用。你回答解決了這個問題,讓我看看對方的位置。 – DBD