2014-01-31 128 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:不会因为计时器已经启动而返回。所以,这段代码在我看来至少有两个错误。