直接进入正题,下面聊聊iOS常用的三种延时方式
1.[self performSelector:@selector(delayMethod) withObject:nil afterDelay:1.0f]
此方法事实上是在其内部创建了个Timer并添加到当前的runloop中,如果当前线程没有runloop那么该方法就会失效,这里我想解释一下,在创建子线程时并不会创建runloop,以前我一直以为子线程创建了runloop只是没有启动而已,你现在百度依然会看到这种论调,子线程的runloop只会在你获取的时候才会去创建,因为它是采用懒加载的
此方法可以在子线程中运行
2.[NSTimer scheduledTimerWithTimeInterval:1.0f target:self selector:@selector(delayMethod) userInfo:nil repeats:NO];
Timer在使用上面方法声明时,也会自动的将其加入到当前的runloop中,这也就是为什么NSTime的创建和释放必须在同一个线程中才行。timer 如果后面的repeat为NO时它是自动执行完后调用invalidate
这里注意Timer 使用上面的声明方法或者 scheduledTimeWithTimeInterval:invacation:repeats:均会将timer自动加入当前的runloop。
使用其他方法声明时需要手动加入runloop。如果在子线程中你没有创建runloop它也是不会运行的。
此方法可以在子线程中运行
3.GCD延时
这个相对于上面两个来说方便的在于子线程中,GCD延时可以直接使用,而不用获取当前线程的runloop。以前看过一篇博客中提到,GCD延时它是到时间后,会将当前的方法提到队列中,而不是像上面两个直接执行@selector里的方法。
当然还有其他不常见的延时方式,这里不表,1 和 2两种延时操作在执行过程中(也即是延时操作还没执行到方法时中途停止)均可以取消,而GCD的延时停止我还没发现方法
定时器一定准确吗?我想你们都知道答案
有什么错漏之处,请大家勘误!