浅析NSRunloop

欢迎关注”iOS开发之道”的微博和微信帐号,一起交流学习。
微博:iOS开发之道 

微信:ioszhidao

image


  通常在程序中我们需要处理各种外部事件,特别是客户端程序,比如处理鼠标点击、屏幕触摸等事件。最简单的形式,我们用一个while循环,去轮询各类事件:

while(e = nextEvent()){
    processEvent(e);
}

  这个是一个主动的轮询,很简单,但是非常低效。即使在没有任何事件,我们的当前线程也会不断地轮询。
  那我们能否这么设计:没有事件的时候让线程休眠,有事的时候唤醒线程进行处理。这个机制是与操作系统相关的,应用进程没有办法实现,因为需要操作系统来唤醒应用进程。在iOS中我们把这个技术叫Runloop,由NSRunloop实现,从名字可以看出来是原来loop的替代者。
1.基本原理

从上图可以看出,启动Runloop后线程会休眠直到时钟、网络等事件出现,然后在Runloop中调用相应的处理函数,处理完成后继续休眠。
2.Runloop Modes
  Runloop需要响应所有的input sources发出的event吗?否. 可以通过Runloop Modes来过滤。你可以简单的把这些modes当作event filter或者input source filter. 每一个mode对应一系列input sources,其它sources发出的event,该loop不接处理。
3.Runloop可以嵌套
  你可以理解成while循环的嵌套,当前Runloop退出后,会回到上一层Runloop,一个事件如果当前Runloop不接受,那么会留给下一个Runloop处理。
4.Runloop的常用方式
1)创建

//常用方式, 若当前无runloop,会自动创建一个
[[NSRunLoop currentRunLoop]

2)运行

[[NSRunLoop currentRunLoop] run]

如果这个时候没有一个input source,比如timer, port, selector,run方法会失败,直接返回NO,否则会运行直到某个date或者有event发生。

5.示例
  在多线程的时候通常需要使用Runloop,比如创建了一个线程用户处理所有的网络请求.

//创建一个线程
[NSThread detachNewThreadSelector:@selector(runThread) toTarget:self withObject:nil]; 
- (void)runThread{
    @autoreleasepool { //为当前线程建立autoreleasepool

    //启动一个selector,该source会保证NSRunloop运行起来
    [self performSelector:@selector(fakeLoop) withObject:nil afterDelay:24*60*60]; 
    while ([[NSThread currentThread] isCancelled] == NO) {
        //每隔自动5s唤醒自己1次,用来清理autorelease pool,释放内存
        [[NSRunLoop currentRunLoop] runUntilDate:[NSDate dateWithTimeIntervalSinceNow:5.0]]; 
       }
    }
}

//保持总有1个selector事件在Runloop上,否则没有NSURLConnection执行时, Runloop会很快退出
- (void)fakeLoop{
    [self performSelector:@selector(fakeLoop) withObject:nil afterDelay:24*60*60];
}

- (void)executeRequest:(NSURLRequest*)aRequest{
    NSURLConnection *aConnection = [[NSURLConnection alloc] initWithRequest:aRequest delegate:self];
    [aConnection start];
}

欢迎关注”iOS开发之道”的微博和微信帐号,一起交流学习。
微博:iOS开发之道 

微信:ioszhidao

image

  • 0
    点赞
  • 0
    收藏
    觉得还不错? 一键收藏
  • 0
    评论
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值