#import "ViewController.h"
@interface ViewController ()
@property(nonatomic,assign)NSInteger count;
@end
@implementation ViewController
- (void)viewDidLoad {
[super viewDidLoad];
//单利
// static dispatch_once_t onceToken;
// dispatch_once(&onceToken,^{
//
// });
//线程互斥
//创建线程锁
NSLock *lock =[[NSLock alloc]init];
//为了防止循环引用
self.count =100;//票数
//创建并行队列
dispatch_queue_t queue =dispatch_queue_create("com.selltikets.www", DISPATCH_QUEUE_CONCURRENT);
__weak ViewController *weakself = self;
for (int i=0; i<10; i++) {
dispatch_async(queue, ^{
[lock lock];//枷锁
for (int j =0; j<10; j++) {
NSLog(@"买到了第%ld张票",weakself.count);
weakself.count--;
}
[lock unlock];//解锁
});
}
// Do any additional setup after loading the view, typically from a nib.
}
/*1.GCD是最简单的多线程,也是效果最高的一种方式,全部是C语言代码编码编写的API,也是是苹果公司主推的一种多线程
2.GCD 通过queue来实现多线程
3.GCD里面有多重queue 一种是串行serial一种是并行concurrent.
*/
//串行队列
- (IBAction)serialqueue:(UIButton *)sender {
//关键字serial 特点,第一个任务执行完成,第二个任务才开始执行,一次类推
//有两种方式
#pragma mark ---串行队列第一种
// dispatch_queue_t queue =dispatch_get_main_queue();
// //往队列里面添加任务
// dispatch_async(queue, ^{
// NSLog(@"这是第一个任务,当前线程%@,是否主线程%d",[NSThread currentThread],[[NSThread currentThread]isMainThread]);
// });
// dispatch_async(queue, ^{
// NSLog(@"这是第二个任务,当前任务是%@,是否是主线程%d",[NSThread currentThread],[[NSThread currentThread]isMainThread]);
// });
// dispatch_async(queue, ^{
// NSLog(@"这是第三个任务,当前任务是%@,是否是主线程%d",[NSThread currentThread],[[NSThread currentThread]isMainThread]);
// });
// dispatch_async(queue, ^{
// NSLog(@"这是第四个任务,这是当前线程%@是否是主线程%d",[NSThread currentThread],[[NSThread currentThread]isMainThread]);
// });
#pragma mark ---串行队列第二种--------------
/*
获取串行队列第二种方式:自己创建队列,
*
*
穿件串行队列的第二种方式
@Pram "serialQueue" 队列的名字(苹果主推使用反向域名去命名)
@pram DISPATCH_QUEUE_SERIAL 队列的类型
手动创建的串行不在主线程中
*/
//
// dispatch_queue_t queue =dispatch_queue_create("com.serialQueue.www", DISPATCH_QUEUE_SERIAL);
// dispatch_async(queue, ^{
// NSLog(@"这是第一个任务,当前线程是%@是否是主线程%d",[NSThread currentThread],[[NSThread currentThread]isMainThread]);
// });
// dispatch_async(queue, ^{
// NSLog(@"这是第二个任务呀当前线程%@,是否是主线程%d",[NSThread currentThread],[[NSThread currentThread]isMainThread]);
// });
// dispatch_async(queue, ^{
// NSLog(@"这是第三个任务,当前任务是:%@是否是主线程%d",[NSThread currentThread],[[NSThread currentThread]isMainThread]);
// });
// dispatch_async(queue, ^{
// NSLog(@"这是第四个任务,当前任务是%@是否是主线程%d",[NSThread currentThread],[[NSThread currentThread]isMainThread]);
// });
}
//并行队列
- (IBAction)concurrentQueue:(UIButton *)sender {
//concurrent 特点:第一个任务执行开始之后,第二个任务,不等第一个执行完毕,直接开始执行.依次类推,后面的任务跟前面的没有关系,先添加的任务不一定先执行,后面添加的不一定最后执行.并行队列会根据队列里面的任务数量CPU使用情况开辟最合适的线程数量,去完成队列里的任务.
//创建有两种方式
#pragma mark -----concurentQueue--第一种方式-------
// dispatch_queue_t queue=dispatch_queue_create("com.concurrentQueue.www", DISPATCH_QUEUE_CONCURRENT);
// dispatch_async(queue, ^{
// NSLog(@"%@%d",[NSThread currentThread],[[NSThread currentThread]isMainThread]);
// });
// dispatch_async(queue, ^{
// NSLog(@"第一个任务当前线程%@是否是主线程%d",[NSThread currentThread],[[NSThread currentThread]isMainThread]);
// });
// dispatch_async(queue, ^{
// NSLog(@"第二个任务当前线程%@是否是主线程%d",[NSThread currentThread],[[NSThread currentThread]isMainThread]);
// });
// dispatch_async(queue, ^{
// NSLog(@"第三个任务当前线程%@是否是主线程%d",[NSThread currentThread],[[NSThread currentThread]isMainThread]);
// });
// dispatch_async(queue, ^{
// NSLog(@"第四个任务,当前线程%@是否是主线程%d",[NSThread currentThread],[[NSThread currentThread]isMainThread]);
// });
#pragma mark -----concurrentQueue__第二种创建方式
//创建globalqueue是苹果里面的全局队列,有四个优先级 第一个参数DISPATCH_QUEUE_PRIORITY_DEFAULT 队列的优先级, 第二个是预留的参数,为了以后使用,目前还没使用写0;
//#define DISPATCH_QUEUE_PRIORITY_HIGH 2
//#define DISPATCH_QUEUE_PRIORITY_DEFAULT 0
//#define DISPATCH_QUEUE_PRIORITY_LOW (-2)
//#define DISPATCH_QUEUE_PRIORITY_BACKGROUND INT16_MIN
dispatch_queue_t queue= dispatch_get_global_queue(DISPATCH_QUEUE_PRIORITY_DEFAULT, 0);
dispatch_async(queue, ^{
NSLog(@"第一个任务当前线程%@是否主线程%d",[NSThread currentThread],[[NSThread currentThread]isMainThread]);
});
dispatch_async(queue, ^{
NSLog(@"第二个任务当前线程%@是否主线程%d",[NSThread currentThread],[[NSThread currentThread]isMainThread]);
});
dispatch_async(queue, ^{
NSLog(@"第三任务当前线程%@是否主线称%d",[NSThread currentThread],[[NSThread currentThread]isMainThread]);
});
dispatch_async(queue, ^{
NSLog(@"第四个任务当前 线程%@是否主线程%d",[NSThread currentThread],[[NSThread currentThread]isMainThread]);
});
dispatch_async(queue, ^{
NSLog(@"第五个任务当前线程%@是否主线程%d",[NSThread currentThread],[[NSThread currentThread]isMainThread]);
});
dispatch_async(queue, ^{
NSLog(@"第六个任务当前线程%@是否主线程%d",[NSThread currentThread],[[NSThread currentThread]isMainThread]);
});
dispatch_async(queue, ^{
NSLog(@"第七个任务当前线程%@是否主线程%d",[NSThread currentThread],[[NSThread currentThread]isMainThread]);
});
dispatch_async(queue, ^{
NSLog(@"第八个任务当前线程%@是否主线成%d",[NSThread currentThread ],[[NSThread currentThread]isMainThread]);
});
dispatch_async(queue, ^{
NSLog(@"第九个任务当前线程%@是否主线程%d",[NSThread currentThread],[[NSThread currentThread]isMainThread]);
});
dispatch_async(queue, ^{
NSLog(@"第十个任务当前线程%@是否主线程%d",[NSThread currentThread],[[NSThread currentThread]isMainThread]);
});
}
//延迟执行代码(dispatch_after 可以再任何队列中执行,串行 并行,都可以);
- (IBAction)afterbutton:(UIButton *)sender {
/*
第一种
*/
// dispatch_after(dispatch_time(DISPATCH_TIME_NOW, (int64_t)(3 * NSEC_PER_SEC)), dispatch_get_main_queue(), ^{
// NSLog(@"%@%d",[NSThread currentThread],[NSThread isMainThread]);
// });
//第二种
dispatch_time_t seconds =dispatch_time(DISPATCH_TIME_NOW, (int64_t)(3 * NSEC_PER_SEC));
//创建一个全局队列
dispatch_queue_t queue =dispatch_get_global_queue(0, 0);
//添加到队列中
dispatch_after(seconds, queue, ^{
NSLog(@" 我是延迟任务当前任务线程%@是否是主线程 %d",[NSThread currentThread],[[NSThread currentThread]isMainThread] );
});
}//方法结尾括号
//线程组
- (IBAction)groupbutton:(UIButton *)sender {
//线程组:disoatch_group_t主要是吧一些不想关的任务就归为一组
//组里面放的是队列
//dispatch_group_async给组里面的队列添加任务
//dispatch_group_notify 作用是监听组里面的任务,等到组里面的任务全部执行完之后,才会执行里面的任务.
//1.创建组
dispatch_group_t group = dispatch_group_create();
//2.创建全局队列
dispatch_queue_t queue =dispatch_get_global_queue(0, 0);
//3.往组里添加队列
dispatch_group_async(group, queue, ^{
NSLog(@"我是第一个任务当前线程%@是否是主线程%d",[NSThread currentThread],[[NSThread currentThread]isMainThread]);
});
dispatch_group_notify(group, queue, ^{
NSLog(@"我是最后一个任务当前线程%@是否主线程%d",[NSThread currentThread],[[NSThread currentThread]isMainThread]);
});
dispatch_group_async(group, queue, ^{
NSLog(@"这是第二个任务当前线程%@是否主线程%d",[NSThread currentThread ],[[NSThread currentThread]isMainThread]);
});
dispatch_group_async(group, queue, ^{
NSLog(@"我是第三个任务当前线程%@是否主线程%d",[NSThread currentThread],[[NSThread currentThread]isMainThread]);
});
}//方法结尾括号
//同时进行读写
- (IBAction)readandwriteatsametime:(UIButton *)sender {
//数据库的读取 可以并发执行,通过GCD里面的并行去实现
//数据库的写入,只能串发执行,通过GCD里面的串行队列去实现;
//但是真正的项目肯定是既有数据的读写也有数据的写入;如何解决" dispatch _barrier_async 在它之前的任务可以区域并发执行,在他之后的任务也可以并发执行
//创建一个并行队列
dispatch_queue_t queue =dispatch_queue_create("con.concurrent.www", DISPATCH_QUEUE_CONCURRENT);
dispatch_async(queue, ^{
NSLog(@"第一任务当前线程%@是否主线成%d",[NSThread currentThread],[[NSThread currentThread]isMainThread]);
});
dispatch_async(queue, ^{
NSLog(@"第二任务,当前线程%@是否主线程%d",[NSThread currentThread],[[NSThread currentThread]isMainThread]);
});
dispatch_async(queue, ^{
NSLog(@"第三任务当前先成%@是否主线程%d",[NSThread currentThread],[[NSThread currentThread]isMainThread]);
});
dispatch_async(queue, ^{
NSLog(@"第四线程当前线程%@是否主线成%d",[NSThread currentThread],[[NSThread currentThread]isMainThread]);
});
dispatch_async(queue, ^{
NSLog(@"第五任务当前任务%@是否主线程%d",[NSThread currentThread],[[NSThread currentThread]isMainThread]);
});
dispatch_barrier_async(queue, ^{
NSLog(@"我正在读取数据%@是否主线程%d",[NSThread currentThread],[[NSThread currentThread]isMainThread]);
});
dispatch_async(queue, ^{
NSLog(@"第六人物当前线程%@是否主线程%d",[NSThread currentThread],[[NSThread currentThread]isMainThread]);
});
dispatch_async(queue, ^{
NSLog(@"第七任务当前线程%@是否主线程%d",[NSThread currentThread],[[NSThread currentThread]isMainThread]);
});
dispatch_async(queue, ^{
NSLog(@"第八任务呀当前线程%@是否主线程%d",[NSThread currentThread],[[NSThread currentThread]isMainThread]);
});
dispatch_async(queue, ^{
NSLog(@"第九任务当前线程%@是否主线程%d",[NSThread currentThread],[[NSThread currentThread]isMainThread]);
});
dispatch_async(queue, ^{
NSLog(@"第十个任务当前线程%@是否主线程%d",[NSThread currentThread ],[[NSThread currentThread]isMainThread]);
});
}
//多次执行
- (IBAction)moretimes:(UIButton *)sender {
NSArray *array =@[@"1",@"2",@"3"];
//同城和数组配合使用
dispatch_queue_t queue =dispatch_get_global_queue(0, 0);
/*
第一个参数 次数
第二个参数 队列
第三个参数 任务
*/
//index:记录当前执行的第几次 ,是小于随机次数的
dispatch_apply(3, queue, ^(size_t index ) {
NSLog(@"%@",array[index]);
});
}
//async和sync的区别
- (IBAction)syncandasyncdiffrent:(UIButton *)sender {
//async不等block体执行完毕就去执行下面的代码
//sync 会等block体执行完毕之后才会执行block;
dispatch_queue_t queue=dispatch_get_global_queue(0, 0);
// dispatch_async(queue, ^{
// NSLog(@"这是第一个任务");
// });
// NSLog(@"呵呵");
// dispatch_async(queue, ^{
// NSLog(@"这是第二个任务");
// });
// NSLog(@"哦");
dispatch_sync(queue, ^{
NSLog(@"第一个任务");
});
NSLog(@"heh");
dispatch_sync(queue, ^{
NSLog(@"第二个任务");
});
NSLog(@"o");
}//
//gcd调用函数指针
- (IBAction)functionpointer:(UIButton *)sender {
dispatch_queue_t queue=dispatch_get_global_queue(0, 0);
/*
第二个参数<#void *context#>函数参数的内容
第三个参数<#dispatch_function_t work#> 函数(函数的返回值为void 参数类型必须为void)
*/
dispatch_async_f(queue, @"hehe", function);
}//
void function(void *context){
NSLog(@"%@",context);
printf("o");
}