dispatch_queue_create方法来创建自己定义的队列,那么自己创建的队列也分为串行和并行两种,对于串行队列,线程池只提供一个线程来执行队列中的任务,并且任务是根据FIFO的原则加入到线程中的,只有先加入到线程中的任务被执行完毕了彩绘执行后加入线程中的任务。
dispatch_queue_t queue_Serial = dispatch_queue_create("queueSerial", DISPATCH_QUEUE_SERIAL);//串行队列,按照fifo规则,先加入的block 会被执行,只有先被加入队列的block 执行完毕后才会执行后加入的block
dispatch_queue_t queue_Concurrent = dispatch_queue_create("queueConcurrent", DISPATCH_QUEUE_CONCURRENT);//并行队列。不论block加入的顺序如何,他们会在队列中并发执行。
<pre name="code" class="objc">dispatch_async(queue_Serial, ^(void){
int sum = 0;
for (int i=0; i<3; i++) {
sum += i;
NSLog(@"block1 ---- %d",i);
}
});
dispatch_async(queue_Serial, ^(void){
int sum = 0;
for (int i=0; i<3; i++) {
sum += i;
NSLog(@"block2 ---- %d",i);
}
});
执行结果应该是先打印了第一个block块中的结果,待第一个block块中打印结束后才会打印出第二个block块中的结果。
2015-03-12 09:31:41.079 CoreDataExp[562:114674] block1 ---- 0
2015-03-12 09:31:41.079 CoreDataExp[562:114674] block1 ---- 1
2015-03-12 09:31:41.079 CoreDataExp[562:114674] block1 ---- 2
2015-03-12 09:31:41.080 CoreDataExp[562:114674] block2 ---- 0
2015-03-12 09:31:41.080 CoreDataExp[562:114674] block2 ---- 1
2015-03-12 09:31:41.080 CoreDataExp[562:114674] block2 ---- 2
而对于并行队列,不论任务或者block块加入的顺序如何,他们都会并发执行。
dispatch_async(queue_Concurrent, ^(void){
int sum = 0;
for (int i=0; i<5; i++) {
sum += i;
NSLog(@"block1 ---- %d",i);
}
});
dispatch_async(queue_Concurrent, ^(void){
int sum = 0;
for (int i=0; i<5; i++) {
sum += i;
NSLog(@"block2 ---- %d",i);
}
});
执行的结果应该是block1和block2中的打印结果很可能是交错在一起的,因为他们是并发执行不分任务加入的先后顺序的。2015-03-12 09:33:46.052 CoreDataExp[606:128452] block1 ---- 0
2015-03-12 09:33:46.053 CoreDataExp[606:128452] block1 ---- 1
2015-03-12 09:33:46.052 CoreDataExp[606:128453] block2 ---- 0
2015-03-12 09:33:46.053 CoreDataExp[606:128452] block1 ---- 2
2015-03-12 09:33:46.053 CoreDataExp[606:128453] block2 ---- 1
2015-03-12 09:33:46.053 CoreDataExp[606:128452] block1 ---- 3
2015-03-12 09:33:46.053 CoreDataExp[606:128453] block2 ---- 2
2015-03-12 09:33:46.053 CoreDataExp[606:128452] block1 ---- 4
2015-03-12 09:33:46.053 CoreDataExp[606:128453] block2 ---- 3
2015-03-12 09:33:46.053 CoreDataExp[606:128453] block2 ---- 4
dispatch_after 的使用(使加入的任务在某一时间后才执行,实际上是在某一段时间后才将任务或者block块加入到队列中进行执行)
在使用该方法之前需要定义一个延迟的时间。
dispatch_time_t time = dispatch_time(DISPATCH_TIME_NOW, (int64_t)(10*NSEC_PER_SEC));//获取一个dispatch_time_t类型的值
//在指定时间之后再将block加入到队列进行执行。
NSEC_PER_SEC代表秒,另外还有
#define NSEC_PER_USEC 1000ull /* nanoseconds per microsecond */
#define USEC_PER_SEC 1000000ull /* microseconds per second */
#define NSEC_PER_SEC 1000000000ull /* nanoseconds per second */
#define NSEC_PER_MSEC 1000000ull /* nanoseconds per millisecond */
dispatch_after(time, queue_Serial, ^(void){
NSLog(@"==============================");
});
结果应该是在十秒之后才会打印出该block中的语句。dispatch_group_t 的使用
dispatch_group_async可以实现监听一组任务是否完成,完成后得到通知执行其他的操作。这个方法很有用,比如你执行六个任务,当六个任务都完成后你才通知界面说完成的
dispatch_queue_t queueConcurrentGroup = dispatch_queue_create("", DISPATCH_QUEUE_CONCURRENT);
dispatch_group_t group = dispatch_group_create();
dispatch_group_async(group, queueConcurrentGroup, ^(void){
printf("1 \n");
});
dispatch_group_async(group, queueConcurrentGroup, ^(void){
printf("2 \n");
});
dispatch_group_async(group, queueConcurrentGroup, ^(void){
printf("3 \n");
});
dispatch_group_async(group, queueConcurrentGroup, ^(void){
printf("4 \n");
});
dispatch_group_async(group, queueConcurrentGroup, ^(void){
printf("5 \n");
});
dispatch_group_async(group, queueConcurrentGroup, ^(void){
printf("6 \n");
});
dispatch_group_notify(group, queueConcurrentGroup, ^(void){
printf("completed ! \n");
});
打印输出的结果应该是:
1
3
4
5
6
2
completed !
dispatch_group_wait
可以使当前线程处于等待状态,只有在之前创建的任务都执行完毕后才会执行接下来加入的任务。
dispatch_barrier_async 会在该方法执行之前加入的block任务都执行完毕后才会执行后续的任务。能够实现锁的作用,例如对文件的读写,只有在之前的度任务执行完毕后才会执行写任务,避免读到脏数据。
NSUserDefaults * userDefault = [NSUserDefaults standardUserDefaults];
[userDefault setValue:@"2" forKey:@"Integer_Key"];
dispatch_queue_t globleQueue = dispatch_get_global_queue(DISPATCH_QUEUE_PRIORITY_DEFAULT, 0);
dispatch_async(globleQueue, ^(void){
[self readFile];
});
dispatch_async(globleQueue, ^(void){
[self readFile];
});
dispatch_async(globleQueue, ^(void){
[self readFile];
});
dispatch_async(globleQueue, ^(void){
[self readFile];
});
dispatch_barrier_async(globleQueue, ^(void){
[self writeFile:8];
[self readFile];
});
dispatch_async(globleQueue, ^(void){
[self writeFile:10];
});
dispatch_async(globleQueue, ^(void){
[self readFile];
});
dispatch_async(globleQueue, ^(void){
[self writeFile:12];
});
dispatch_async(globleQueue, ^(void){
[self readFile];
});
dispatch_apply 能够重复执行某一个任务多次,例如对数组中的成员进行遍历,多个线程并发遍历,提高遍历速度的同时还能知道当前遍历所在的索引。
NSArray *array = [NSArray arrayWithObjects:@"54677",
@"11121",
@"12123",
@"1244444",
@"112455",
@"sdfsadfadfad",
@"sdfadfa",
@"sdfads23sd",
nil];
dispatch_queue_t concurrentQueueApply = dispatch_queue_create("queueApply", DISPATCH_QUEUE_CONCURRENT);
dispatch_async(concurrentQueueApply, ^(void){
dispatch_apply([array count], concurrentQueueApply, ^(size_t index){
NSString * string = [array objectAtIndex:index];
NSLog(@"%@=======%zu",string,index);
if ([string isEqualToString:@"<span style="font-family: Arial, Helvetica, sans-serif;">sdfsadfadfad</span><span style="font-family: Arial, Helvetica, sans-serif;">"]) {</span>
NSLog(@"%@---%zu",string,index);
}
});
NSLog(@"apply completed !");
});