代码如下:
1 #import "ViewController.h"
2 @interface ViewController ()
3 /** 定时器(不用带*,因为dispatch_source_t本身是一个类) */
4 @property (strong, nonatomic)dispatch_source_t timer;
5 @end
6 @implementation ViewController
7 - (void)viewDidLoad {
8 [super viewDidLoad];
9 }
10
11 int count = 0;
12 - (void)touchesBegan:(NSSet<UITouch *> *)touches withEvent:(UIEvent *)event
13 {
14 //获得队列
15 dispatch_queue_t queue = dispatch_get_global_queue(0, 0);
16 //创建一个定时器(dispatch_source_t本质还是一个OC对象,需要用强引用)
17 self.timer = dispatch_source_create(DISPATCH_SOURCE_TYPE_TIMER, 0, 0, queue);
18 //设置定时器的各种属性(几时开始任务,每隔多久执行一次)
19 //GCD的时间参数是纳秒(1秒=10的9次方纳秒)
20 dispatch_time_t start = dispatch_time(DISPATCH_TIME_NOW, (int64_t)3.0 * NSEC_PER_SEC); //表示三秒后开始执行
21 uint64_t interval = (uint64_t)(2.0 * NSEC_PER_SEC);//表示时间间隔2.0秒执行一次
22 dispatch_source_set_timer(self.timer, start, interval, 0);
23 //设置回调
24 dispatch_source_set_event_handler(self.timer, ^{
25 NSLog(@"------%@-----",[NSThread currentThread]);
26 });
27 count++;
28 if (count == 3) {
29 //当执行完3次之后停止(注意是强引用,所以设置为空)
30 dispatch_cancel(self.timer);
31 self.timer = nil;
32 }
33 //启动定时器
34 dispatch_resume(self.timer);
35 }
36 @end
上面有一个明显的错误,只有把
1 count++;
2 if (count == 3) {
3 //当执行完3次之后停止(注意是强引用,所以设置为空)
4 dispatch_cancel(self.timer);
5 self.timer = nil;
6 }
放入到回调内(dispatch_source_set_event_handler方法中),到执行3次的之后才能停止。
因为如果放在外面,后面的代码只执行一次,count永远为0
放入回调中,定时器每执行一次都会调用一次dispatch_source_set_event_handler,让count递增一次,到了执行第三次后就会停止!!
注:
1、NSTimer不准可以用GCD的定时器,(精确到纳秒)
2、GCD定时器不受RunLoop中Mode的影响