我读了很多关于 NSRunLoop
的帖子,比如 this , this , this .但无法弄清楚 NSRunLoop
实际上做了什么
我平时看到的是工作线程
wthread = [[NSThread alloc] initWithTarget:self selector:@selector(threadProc) object:nil];
[wthread start];
里面有一个 NSRunLoop
- (void)threadProc
{
NSAutoreleasePool* pool1 = [[NSAutoreleasePool alloc] init];
BOOL isStopped = NO;
NSRunLoop *runloop = [NSRunLoop currentRunLoop];
[runloop addPort:[NSMachPort port] forMode:NSDefaultRunLoopMode];
while (!isStopped)
{
{
NSAutoreleasePool* pool2 = [[NSAutoreleasePool alloc] init];
[runloop runMode:NSDefaultRunLoopMode
beforeDate:[NSDate distantFuture]];
[pool2 release];
}
}
[pool1 release];
}
然后主线程将一些工作传递给这个 wthread
[self performSelector:@selector(someWork:) onThread:wthread withObject:nil waitUntilDone:NO];
关于将工作从主线程传递到工作线程,我看到很多人这样做。为什么这里需要 NSRunLoop ?它有什么作用?
我看到NSRunLoop
是用来管理事件的,为什么在threadProc
里面除了调用runMode就什么都没有了?
最佳答案
您展示的示例是 Cocoa 惯用语,用于创建一个线程,该线程将在方法 -threadProc
退出后继续运行。为什么?
因为:
- 您创建的
NSRunLoop
实例至少有一个输入源 ([NSMachPort port]
) - 您已使用
runMode:beforeDate
显式启动运行循环
如果不添加输入源并显式启动运行循环,线程将终止。
顺便说一句,尽管运行循环对于管理事件和某些异步任务仍然至关重要,但我不会将 NSThread
视为如今在 Cocoa 应用程序中构建大多数异步工作的默认方式。 GCD 是封装后台工作的一种更简洁的方法。
编辑:
将工作提交到 GCD 中的串行队列:
@interface Foo : NSObject
@end
@implementation Foo {
dispatch_queue_t _someWorkerQueue;
}
- (id)init {
self = [super init];
if( !self ) return nil;
_someWorkerQueue = dispatch_queue_create("com.company.MyWorkerQueue", 0);
return self;
}
- (void)performJob {
dispatch_async(_someWorkerQueue, ^{
//do some work asynchronously here
});
dispatch_async(_someWorkerQueue, ^{
//more asynchronous work here
});
}
@end
关于ios - NSRunLoop 是做什么的?,我们在Stack Overflow上找到一个类似的问题: https://stackoverflow.com/questions/16477433/