2014-01-31 124 views
0

我有一些關於如何在線程中使用NSRunLoop的問題。在Apple的線程編程指南中,它提到「你的代碼提供了用於實現運行循環的實際循環部分的控制語句 - 換句話說,你的代碼提供了驅動運行循環的while或for循環。」因此,使用NSURLConnection的時候在一個新的線程異步加載數據,我寫了下面的代碼和它的工作:使用「while循環」或「for循環」在線程中驅動NSRunLoop

... 
.... 
NSURLConnection* connection = [[NSURLConnection alloc] initWithRequest:request delegate:self startImmediately:NO]; 
[NSThread detachNewThreadSelector:@selector(downloadThread:) toTarget:self withObject:nil]; 
.... 
... 

選擇「downloadThread」是一個新的線程的入口點,以下是「downloadThread」的代碼:

- (int) downloadThread:(id)option { 
    BOOL ret; 
    [connection scheduleInRunLoop:[NSRunLoop currentRunLoop] forMode:NSDefaultRunLoopMode]; 
    [connection start]; 
    while (finished == NO) { 
     ret = [[NSRunLoop currentRunLoop] runMode:NSDefaultRunLoopMode beforeDate:[NSDate distantFuture]]; 
    } 
    return 1; 
} 

這裏的問題,NSRunLoop是一個循環,我們爲什麼要使用循環語句「而(完成== NO)」來控制NSRunLoop?儘管蘋果的文件提到這一點,但我只是不」不明白。在另一隻手,使用計時器時,我們並不需要一個循環語句來控制NSRunLoop,和它的作品,就像這樣:

... 
.... 
NSTimer* _timer = [NSTimer timerWithTimeInterval:1 target:object selector:@selector(timerFunc) userInfo:nil repeats:YES]; 
[[NSRunLoop currentRunLoop] addTimer:_timer forMode:NSDefaultRunLoopMode]; 
[_timer fire]; 
[[NSRunLoop currentRunLoop] runMode:NSDefaultRunLoopMode beforeDate:[NSDate distantFuture]]; 
.... 
... 

所以,在什麼情況下,我們應該使用一個循環語句來控制NSRunLoop?

+6

'NSURLConnection'默認在後臺執行所有操作。你不需要任何這種線程代碼來正確使用它。 – rmaddy

回答

0

閱讀docs-[NSRunLoop runMode:beforeDate:]。該方法在處理單個輸入源後返回。因此,如果您希望在發生某些特定事件之前繼續處理輸入源,則必須循環執行。

我不確定那個計時器代碼來自哪裏,但不能保證一旦打電話給-runMode:beforeDate:就可以啓動計時器。另外,-runMode:beforeDate:不會因爲計時器已經啓動而返回。所以,這段代碼在我看來至少有兩個錯誤。