GCD死锁,及同步、异步、串行和并行队列组合情形

dispatch_queue_t queue2 = dispatch_get_global_queue(, ); dispatch_async(queue2, ^{
for (int i = ; i < ; i++) {
NSLog(@"执行任务3-----%@", [NSThread currentThread]);
}
}); for (int i = ; i < ; i++) {
NSLog(@"执行任务1-----%@", [NSThread currentThread]);
}
//打印
-- ::28.408678+ MJ_iOS_Test[:] 执行任务1-----<NSThread: 0x600000c16980>{number = , name = main}
-- ::28.408685+ MJ_iOS_Test[:] 执行任务3-----<NSThread: 0x600000c7b780>{number = , name = (null)}
-- ::28.408935+ MJ_iOS_Test[:] 执行任务1-----<NSThread: 0x600000c16980>{number = , name = main}
-- ::28.408935+ MJ_iOS_Test[:] 执行任务3-----<NSThread: 0x600000c7b780>{number = , name = (null)}
-- ::28.409076+ MJ_iOS_Test[:] 执行任务1-----<NSThread: 0x600000c16980>{number = , name = main}
-- ::28.409098+ MJ_iOS_Test[:] 执行任务3-----<NSThread: 0x600000c7b780>{number = , name = (null)}
-- ::28.409185+ MJ_iOS_Test[:] 执行任务1-----<NSThread: 0x600000c16980>{number = , name = main}
-- ::28.409232+ MJ_iOS_Test[:] 执行任务3-----<NSThread: 0x600000c7b780>{number = , name = (null)}
-- ::28.409301+ MJ_iOS_Test[:] 执行任务1-----<NSThread: 0x600000c16980>{number = , name = main}
-- ::28.409618+ MJ_iOS_Test[:] 执行任务3-----<NSThread: 0x600000c7b780>{number = , name = (null)}
-- ::28.409873+ MJ_iOS_Test[:] 执行任务1-----<NSThread: 0x600000c16980>{number = , name = main}
-- ::28.410141+ MJ_iOS_Test[:] 执行任务3-----<NSThread: 0x600000c7b780>{number = , name = (null)}
-- ::28.410480+ MJ_iOS_Test[:] 执行任务1-----<NSThread: 0x600000c16980>{number = , name = main}
-- ::28.410794+ MJ_iOS_Test[:] 执行任务3-----<NSThread: 0x600000c7b780>{number = , name = (null)}
-- ::28.411167+ MJ_iOS_Test[:] 执行任务1-----<NSThread: 0x600000c16980>{number = , name = main}
-- ::28.411486+ MJ_iOS_Test[:] 执行任务3-----<NSThread: 0x600000c7b780>{number = , name = (null)}
---- ::28.411962+ MJ_iOS_Test[:] 执行任务3-----<NSThread: 0x600000c7b780>{number = , name = (null)}
::28.411763+ MJ_iOS_Test[:] 执行任务1-----<NSThread: 0x600000c16980>{number = , name = main}
-- ::28.422231+ MJ_iOS_Test[:] 执行任务1-----<NSThread: 0x600000c16980>{number = , name = main}
-- ::28.422250+ MJ_iOS_Test[:] 执行任务3-----<NSThread: 0x600000c7b780>{number = , name = (null)}
dispatch_queue_t queue1 = dispatch_get_main_queue(); dispatch_sync(queue1, ^{
for (int i = ; i < ; i++) {
NSLog(@"执行任务3-----%@", [NSThread currentThread]);
}
});
//错误

dispatch_queue_t queue3 = dispatch_queue_create("myQueue3", DISPATCH_QUEUE_SERIAL);
NSLog(@"执行任务1----%@", [NSThread currentThread]);
dispatch_async(queue3, ^{
NSLog(@"执行任务2----%@", [NSThread currentThread]);
dispatch_sync(queue3, ^{
NSLog(@"执行任务3----%@", [NSThread currentThread]);
});
NSLog(@"执行任务4----%@", [NSThread currentThread]);
});
NSLog(@"执行任务5----%@", [NSThread currentThread]);
//打印
dispatch_queue_t queue3 = dispatch_queue_create("myQueue3", DISPATCH_QUEUE_SERIAL); dispatch_queue_t queue4 = dispatch_queue_create("myQueue4", DISPATCH_QUEUE_SERIAL); NSLog(@"执行任务1----%@", [NSThread currentThread]); dispatch_async(queue3, ^{ NSLog(@"执行任务2----%@", [NSThread currentThread]); dispatch_sync(queue4, ^{
NSLog(@"执行任务3----%@", [NSThread currentThread]);
}); NSLog(@"执行任务4----%@", [NSThread currentThread]);
}); NSLog(@"执行任务5----%@", [NSThread currentThread]);
//打印
-- ::51.782328+ MJ_iOS_Test[:] 执行任务1----<NSThread: 0x600003661480>{number = , name = main}
-- ::51.782639+ MJ_iOS_Test[:] 执行任务5----<NSThread: 0x600003661480>{number = , name = main}
-- ::51.782678+ MJ_iOS_Test[:] 执行任务2----<NSThread: 0x600003607fc0>{number = , name = (null)}
-- ::51.782818+ MJ_iOS_Test[:] 执行任务3----<NSThread: 0x600003607fc0>{number = , name = (null)}
-- ::51.782955+ MJ_iOS_Test[:] 执行任务4----<NSThread: 0x600003607fc0>{number = , name = (null)}
//分析
<1>dispatch_sync本身运行在子线程中,而该子线程对应的队列为queue3,因此A2(即添加任务本身)存放在queue3中,而3存放在queue4中;
<2>当子线程运行完毕2后(并随即自动销毁),此时系统是从queue3中取出4还是从queue4取出3放到子线程中运行呢?——因为同步,系统不会开辟新的线程,添加的block任务依然运行在当前线程中(number为3的子线程);同时,A2会一直停留在queue3中,直到3执行完毕才会自动销毁,又因为queue3是个串行队列而4排在A2后面,所以A2把4给堵住了,当3运行完毕后,A2销毁,系统就从queue3中取出4放到当前线程中运行;
注:此处将3放到一个并发队列中,效果是一样的;
dispatch_queue_t queue3 = dispatch_queue_create("myQueue3", DISPATCH_QUEUE_SERIAL); NSLog(@"执行任务1----%@", [NSThread currentThread]); dispatch_async(queue3, ^{ NSLog(@"执行任务2----%@", [NSThread currentThread]); dispatch_async(queue3, ^{
NSLog(@"执行任务3----%@", [NSThread currentThread]);
}); NSLog(@"执行任务4----%@", [NSThread currentThread]);
}); NSLog(@"执行任务5----%@", [NSThread currentThread]);
//打印
-- ::46.953030+ MJ_iOS_Test[:] 执行任务1----<NSThread: 0x6000030aa900>{number = , name = main}
-- ::46.953330+ MJ_iOS_Test[:] 执行任务5----<NSThread: 0x6000030aa900>{number = , name = main}
-- ::46.953326+ MJ_iOS_Test[:] 执行任务2----<NSThread: 0x6000030c2880>{number = , name = (null)}
-- ::46.953608+ MJ_iOS_Test[:] 执行任务4----<NSThread: 0x6000030c2880>{number = , name = (null)}
-- ::46.954050+ MJ_iOS_Test[:] 执行任务3----<NSThread: 0x6000030c2880>{number = , name = (null)}
//分析——我门只分析3和4的顺序
<1>因为是异步且queue3非主队列,所以系统理应开辟一个新线程,但是运行完2后,此刻当前线程(number为3的子线程)处于闲置状态,为了节省资源,系统并不会真的开辟一个新线程,所有后面的任务依然会运行在当前子线程中(除非当前线程正在运行中,而同时要异步运行另一个任务,系统才会考虑开启一个新线程,或者手动强行开启一个新线程(异步并发));
<2>首先,我们明确下A2(第二个dispatch_async添加任务本身)、3和4在queue3中的存放顺序:
因为3的存放是由A2在线程上运行完成的,而在编译阶段A2并不会运行,但此时系统会给A2和4分配位置(依据代码顺序)——因此A2和4的存放是在编译阶段完成的,而3的存放是在运行阶段完成的,所以如下图所示
<3>因为异步,所以A2不会停留在queue3中一直等待3执行完毕而是将3添加到queue3中随即自动销毁,因为queue3是个串行队列,此时系统就从queue3中取出4放到当前子线程中运行,待4运行完毕,系统又会取出3放到当前子线程中运行;
说明:dispatch添加block任务(不论异步还是同步),都是在当前线程上运行完成的,因此该block任务的存放位置一定在dispatch后面所有外部任务(后面dispatch中的block任务以此类推)的位置后面———这点,请注意!!!
dispatch_queue_t queue3 = dispatch_queue_create("myQueue3", DISPATCH_QUEUE_SERIAL); dispatch_sync(queue3, ^{
for (int i = ; i < ; i++) {
NSLog(@"执行任务3-----%@", [NSThread currentThread]);
}
}); for (int i = ; i < ; i++) {
NSLog(@"执行任务1-----%@", [NSThread currentThread]);
}
//打印
-- ::57.529267+ MJ_iOS_Test[:] 执行任务3-----<NSThread: 0x60000252ce40>{number = , name = main}
-- ::57.529503+ MJ_iOS_Test[:] 执行任务3-----<NSThread: 0x60000252ce40>{number = , name = main}
-- ::57.529627+ MJ_iOS_Test[:] 执行任务3-----<NSThread: 0x60000252ce40>{number = , name = main}
-- ::57.529771+ MJ_iOS_Test[:] 执行任务3-----<NSThread: 0x60000252ce40>{number = , name = main}
-- ::57.529903+ MJ_iOS_Test[:] 执行任务3-----<NSThread: 0x60000252ce40>{number = , name = main}
-- ::57.530018+ MJ_iOS_Test[:] 执行任务3-----<NSThread: 0x60000252ce40>{number = , name = main}
-- ::57.530147+ MJ_iOS_Test[:] 执行任务3-----<NSThread: 0x60000252ce40>{number = , name = main}
-- ::57.530270+ MJ_iOS_Test[:] 执行任务3-----<NSThread: 0x60000252ce40>{number = , name = main}
-- ::57.530418+ MJ_iOS_Test[:] 执行任务3-----<NSThread: 0x60000252ce40>{number = , name = main}
-- ::57.530547+ MJ_iOS_Test[:] 执行任务3-----<NSThread: 0x60000252ce40>{number = , name = main}
-- ::57.530666+ MJ_iOS_Test[:] 执行任务1-----<NSThread: 0x60000252ce40>{number = , name = main}
-- ::57.530898+ MJ_iOS_Test[:] 执行任务1-----<NSThread: 0x60000252ce40>{number = , name = main}
-- ::57.531152+ MJ_iOS_Test[:] 执行任务1-----<NSThread: 0x60000252ce40>{number = , name = main}
-- ::57.549535+ MJ_iOS_Test[:] 执行任务1-----<NSThread: 0x60000252ce40>{number = , name = main}
-- ::57.549711+ MJ_iOS_Test[:] 执行任务1-----<NSThread: 0x60000252ce40>{number = , name = main}
-- ::57.549853+ MJ_iOS_Test[:] 执行任务1-----<NSThread: 0x60000252ce40>{number = , name = main}
-- ::57.549989+ MJ_iOS_Test[:] 执行任务1-----<NSThread: 0x60000252ce40>{number = , name = main}
-- ::57.550113+ MJ_iOS_Test[:] 执行任务1-----<NSThread: 0x60000252ce40>{number = , name = main}
-- ::57.550247+ MJ_iOS_Test[:] 执行任务1-----<NSThread: 0x60000252ce40>{number = , name = main}
-- ::57.550381+ MJ_iOS_Test[:] 执行任务1-----<NSThread: 0x60000252ce40>{number = , name = main}
dispatch_queue_t queue2 = dispatch_get_global_queue(, ); for (int i = ; i < ; i++) {
NSLog(@"执行任务1----%@", [NSThread currentThread]);
} dispatch_async(queue2, ^{ for (int i = ; i < ; i++) {
NSLog(@"执行任务2----%@", [NSThread currentThread]);
} dispatch_sync(queue2, ^{
for (int i = ; i < ; i++) {
NSLog(@"执行任务3----%@", [NSThread currentThread]);
}
}); for (int i = ; i < ; i++) {
NSLog(@"执行任务4----%@", [NSThread currentThread]);
}
}); for (int i = ; i < ; i++) {
NSLog(@"执行任务5----%@", [NSThread currentThread]);
}
//打印
-- ::50.417681+ MJ_iOS_Test[:] 执行任务1----<NSThread: 0x600002e96900>{number = , name = main}
-- ::50.417926+ MJ_iOS_Test[:] 执行任务1----<NSThread: 0x600002e96900>{number = , name = main}
-- ::50.418055+ MJ_iOS_Test[:] 执行任务1----<NSThread: 0x600002e96900>{number = , name = main}
-- ::50.418175+ MJ_iOS_Test[:] 执行任务1----<NSThread: 0x600002e96900>{number = , name = main}
-- ::50.418292+ MJ_iOS_Test[:] 执行任务1----<NSThread: 0x600002e96900>{number = , name = main}
-- ::50.418449+ MJ_iOS_Test[:] 执行任务5----<NSThread: 0x600002e96900>{number = , name = main}
-- ::50.418492+ MJ_iOS_Test[:] 执行任务2----<NSThread: 0x600002ef8680>{number = , name = (null)}
-- ::50.418569+ MJ_iOS_Test[:] 执行任务5----<NSThread: 0x600002e96900>{number = , name = main}
-- ::50.418727+ MJ_iOS_Test[:] 执行任务2----<NSThread: 0x600002ef8680>{number = , name = (null)}
-- ::50.419157+ MJ_iOS_Test[:] 执行任务5----<NSThread: 0x600002e96900>{number = , name = main}
-- ::50.419427+ MJ_iOS_Test[:] 执行任务2----<NSThread: 0x600002ef8680>{number = , name = (null)}
-- ::50.419705+ MJ_iOS_Test[:] 执行任务5----<NSThread: 0x600002e96900>{number = , name = main}
-- ::50.419987+ MJ_iOS_Test[:] 执行任务2----<NSThread: 0x600002ef8680>{number = , name = (null)}
-- ::50.420301+ MJ_iOS_Test[:] 执行任务5----<NSThread: 0x600002e96900>{number = , name = main}
-- ::50.427851+ MJ_iOS_Test[:] 执行任务2----<NSThread: 0x600002ef8680>{number = , name = (null)}
-- ::50.428027+ MJ_iOS_Test[:] 执行任务3----<NSThread: 0x600002ef8680>{number = , name = (null)}
-- ::50.428232+ MJ_iOS_Test[:] 执行任务3----<NSThread: 0x600002ef8680>{number = , name = (null)}
-- ::50.429049+ MJ_iOS_Test[:] 执行任务3----<NSThread: 0x600002ef8680>{number = , name = (null)}
-- ::50.429279+ MJ_iOS_Test[:] 执行任务3----<NSThread: 0x600002ef8680>{number = , name = (null)}
-- ::50.429431+ MJ_iOS_Test[:] 执行任务3----<NSThread: 0x600002ef8680>{number = , name = (null)}
-- ::50.429774+ MJ_iOS_Test[:] 执行任务4----<NSThread: 0x600002ef8680>{number = , name = (null)}
-- ::50.430498+ MJ_iOS_Test[:] 执行任务4----<NSThread: 0x600002ef8680>{number = , name = (null)}
-- ::50.430812+ MJ_iOS_Test[:] 执行任务4----<NSThread: 0x600002ef8680>{number = , name = (null)}
-- ::50.431099+ MJ_iOS_Test[:] 执行任务4----<NSThread: 0x600002ef8680>{number = , name = (null)}
-- ::50.431531+ MJ_iOS_Test[:] 执行任务4----<NSThread: 0x600002ef8680>{number = , name = (null)}
//分析
<1>当主线程(以下简称“T0”)运行完1后,程序走到第一个异步并发,此时系统必然开启一个新线程(以下简称“T1”),该线程运行第一个大block中的内容(以下简称“B1”),而主线程继续运行5,5和第一个大block中的内容的运行互不影响,交替执行,这点没问题;
<2>但是,问题来了—————第一个大block中的内容要先执行哪一个呢?为什么是2跟5交替执行,而其他都是顺序执行呢?
$0:首先要明确一点,不论是串行队列还是并行队列,其内部任务的添加都要遵循先来后到的顺序;
$1:各个队列中任务的位置顺序:主队列中存放三个任务,顺序依次为1、第一个async任务本身(以下简称“A1”)和5,均由主线程来运行并且A1不会等待,所以1和A1执行完毕才能执行5,这点没问题;queue2中存放2、第二个sync任务本身(以下简称“A2”)、3和4四个任务,按照上述分析,dispatch添加的block任务3会在2和4之后,所以存放顺序依次为2、A2、4和3,如下图;
$2:当程序进入B1后A2之前,此时的所有任务都只会运行在当前线程T1中,走到A2时,因为是同步,所以不会开启新线程,因此B1始终运行在T1上;而并发队列只有在异步时才有效,即如果只有一条线程时则只能顺序执行;
$3:因此,T1会先运行2,此时T0在运行5,两条线程互不影响,交替运行;待2运行完后,按顺序系统会从queue2中取出A2放到T1中运行,因为是同步,A2把3添加到queue2队列中后依然停留在queue2中等待3运行完毕而不会立即销毁;
----问题:此时queue2不会死锁吗?系统是从queue2中先取出3还是先取出4放到T1上运行呢?
第一个问题:因为只有一条线程,所以queue2虽为并行队列,但也只能按顺序运行其内部任务,但因为是并行队列,系统是可以从queue2中取出任何一个任务放到线程上运行,场景理解:
死锁:串行队列好比一根独木桥(横向距离刚好只能站住一个人,桥下是悬崖),桥上有ABCDE五个人依次排队进火车站检票入口(有且仅有一个);
同步并行:上述五个人站在大马路上(马路很宽)排队进检票口;
系统:检票员;
因此:如果是死锁,检票员无法跑到D身边让D先进检票口——否则会掉进悬崖;而同步并行就可以;
所以,串行队列,系统要按顺序取队列中的任务;并行,系统可以随机取————这点,请注意!!!;
第二个问题:因为A2一直在等待3运行完毕,即告诉系统要立马将3取出运行;
所以,同步即优先(立马)运行其添加的block任务————这点,请注意!!!
dispatch_queue_t queue1 = dispatch_get_main_queue(); dispatch_async(queue1, ^{
for (int i = ; i < ; i++) {
NSLog(@"执行任务3-----%@", [NSThread currentThread]);
}
}); for (int i = ; i < ; i++) {
NSLog(@"执行任务1-----%@", [NSThread currentThread]);
}
//打印
-- ::24.484445+ MJ_iOS_Test[:] 执行任务1-----<NSThread: 0x600002642940>{number = , name = main}
-- ::24.484665+ MJ_iOS_Test[:] 执行任务1-----<NSThread: 0x600002642940>{number = , name = main}
-- ::24.484837+ MJ_iOS_Test[:] 执行任务1-----<NSThread: 0x600002642940>{number = , name = main}
-- ::24.484978+ MJ_iOS_Test[:] 执行任务1-----<NSThread: 0x600002642940>{number = , name = main}
-- ::24.485116+ MJ_iOS_Test[:] 执行任务1-----<NSThread: 0x600002642940>{number = , name = main}
-- ::24.485296+ MJ_iOS_Test[:] 执行任务1-----<NSThread: 0x600002642940>{number = , name = main}
-- ::24.485430+ MJ_iOS_Test[:] 执行任务1-----<NSThread: 0x600002642940>{number = , name = main}
-- ::24.485566+ MJ_iOS_Test[:] 执行任务1-----<NSThread: 0x600002642940>{number = , name = main}
-- ::24.485698+ MJ_iOS_Test[:] 执行任务1-----<NSThread: 0x600002642940>{number = , name = main}
-- ::24.485815+ MJ_iOS_Test[:] 执行任务1-----<NSThread: 0x600002642940>{number = , name = main}
-- ::24.507778+ MJ_iOS_Test[:] 执行任务3-----<NSThread: 0x600002642940>{number = , name = main}
-- ::24.507968+ MJ_iOS_Test[:] 执行任务3-----<NSThread: 0x600002642940>{number = , name = main}
-- ::24.508119+ MJ_iOS_Test[:] 执行任务3-----<NSThread: 0x600002642940>{number = , name = main}
-- ::24.508252+ MJ_iOS_Test[:] 执行任务3-----<NSThread: 0x600002642940>{number = , name = main}
-- ::24.508388+ MJ_iOS_Test[:] 执行任务3-----<NSThread: 0x600002642940>{number = , name = main}
-- ::24.508541+ MJ_iOS_Test[:] 执行任务3-----<NSThread: 0x600002642940>{number = , name = main}
-- ::24.508695+ MJ_iOS_Test[:] 执行任务3-----<NSThread: 0x600002642940>{number = , name = main}
-- ::24.509382+ MJ_iOS_Test[:] 执行任务3-----<NSThread: 0x600002642940>{number = , name = main}
-- ::24.509973+ MJ_iOS_Test[:] 执行任务3-----<NSThread: 0x600002642940>{number = , name = main}
-- ::24.510909+ MJ_iOS_Test[:] 执行任务3-----<NSThread: 0x600002642940>{number = , name = main}
dispatch_queue_t queue3 = dispatch_queue_create("myQueue3", DISPATCH_QUEUE_SERIAL); dispatch_async(queue3, ^{
for (int i = ; i < ; i++) {
NSLog(@"执行任务3-----%@", [NSThread currentThread]);
}
}); for (int i = ; i < ; i++) {
NSLog(@"执行任务1-----%@", [NSThread currentThread]);
}
//打印
-- ::12.843681+ MJ_iOS_Test[:] 执行任务1-----<NSThread: 0x6000011aae40>{number = , name = main}
-- ::12.843686+ MJ_iOS_Test[:] 执行任务3-----<NSThread: 0x6000011c9e00>{number = , name = (null)}
-- ::12.843933+ MJ_iOS_Test[:] 执行任务3-----<NSThread: 0x6000011c9e00>{number = , name = (null)}
-- ::12.843999+ MJ_iOS_Test[:] 执行任务1-----<NSThread: 0x6000011aae40>{number = , name = main}
-- ::12.844065+ MJ_iOS_Test[:] 执行任务3-----<NSThread: 0x6000011c9e00>{number = , name = (null)}
-- ::12.844208+ MJ_iOS_Test[:] 执行任务3-----<NSThread: 0x6000011c9e00>{number = , name = (null)}
-- ::12.844348+ MJ_iOS_Test[:] 执行任务3-----<NSThread: 0x6000011c9e00>{number = , name = (null)}
-- ::12.844474+ MJ_iOS_Test[:] 执行任务3-----<NSThread: 0x6000011c9e00>{number = , name = (null)}
-- ::12.844482+ MJ_iOS_Test[:] 执行任务1-----<NSThread: 0x6000011aae40>{number = , name = main}
-- ::12.844614+ MJ_iOS_Test[:] 执行任务3-----<NSThread: 0x6000011c9e00>{number = , name = (null)}
-- ::12.844743+ MJ_iOS_Test[:] 执行任务1-----<NSThread: 0x6000011aae40>{number = , name = main}
-- ::12.844769+ MJ_iOS_Test[:] 执行任务3-----<NSThread: 0x6000011c9e00>{number = , name = (null)}
-- ::12.845040+ MJ_iOS_Test[:] 执行任务1-----<NSThread: 0x6000011aae40>{number = , name = main}
-- ::12.845234+ MJ_iOS_Test[:] 执行任务3-----<NSThread: 0x6000011c9e00>{number = , name = (null)}
-- ::12.845559+ MJ_iOS_Test[:] 执行任务1-----<NSThread: 0x6000011aae40>{number = , name = main}
-- ::12.854636+ MJ_iOS_Test[:] 执行任务3-----<NSThread: 0x6000011c9e00>{number = , name = (null)}
-- ::12.855004+ MJ_iOS_Test[:] 执行任务1-----<NSThread: 0x6000011aae40>{number = , name = main}
-- ::12.855578+ MJ_iOS_Test[:] 执行任务1-----<NSThread: 0x6000011aae40>{number = , name = main}
-- ::12.855858+ MJ_iOS_Test[:] 执行任务1-----<NSThread: 0x6000011aae40>{number = , name = main}
-- ::12.856068+ MJ_iOS_Test[:] 执行任务1-----<NSThread: 0x6000011aae40>{number = , name = main}
dispatch_queue_t queue3 = dispatch_queue_create("myQueue3", DISPATCH_QUEUE_SERIAL); dispatch_async(queue3, ^{
for (int i = ; i < ; i++) {
NSLog(@"执行任务3-----%@", [NSThread currentThread]);
}
}); dispatch_async(queue3, ^{
for (int i = ; i < ; i++) {
NSLog(@"执行任务3-2-----%@", [NSThread currentThread]);
}
}); for (int i = ; i < ; i++) {
NSLog(@"执行任务1-----%@", [NSThread currentThread]);
}
//打印
-- ::52.982315+ MJ_iOS_Test[:] 执行任务3-----<NSThread: 0x600000320940>{number = , name = (null)}
-- ::52.982310+ MJ_iOS_Test[:] 执行任务1-----<NSThread: 0x600000356840>{number = , name = main}
-- ::52.982607+ MJ_iOS_Test[:] 执行任务3-----<NSThread: 0x600000320940>{number = , name = (null)}
-- ::52.982607+ MJ_iOS_Test[:] 执行任务1-----<NSThread: 0x600000356840>{number = , name = main}
-- ::52.982759+ MJ_iOS_Test[:] 执行任务1-----<NSThread: 0x600000356840>{number = , name = main}
-- ::52.982759+ MJ_iOS_Test[:] 执行任务3-----<NSThread: 0x600000320940>{number = , name = (null)}
-- ::52.982871+ MJ_iOS_Test[:] 执行任务1-----<NSThread: 0x600000356840>{number = , name = main}
-- ::52.982917+ MJ_iOS_Test[:] 执行任务3-----<NSThread: 0x600000320940>{number = , name = (null)}
-- ::52.982970+ MJ_iOS_Test[:] 执行任务1-----<NSThread: 0x600000356840>{number = , name = main}
-- ::52.983061+ MJ_iOS_Test[:] 执行任务3-----<NSThread: 0x600000320940>{number = , name = (null)}
-- ::52.983401+ MJ_iOS_Test[:] 执行任务1-----<NSThread: 0x600000356840>{number = , name = main}
-- ::52.983668+ MJ_iOS_Test[:] 执行任务3-----<NSThread: 0x600000320940>{number = , name = (null)}
-- ::52.983945+ MJ_iOS_Test[:] 执行任务1-----<NSThread: 0x600000356840>{number = , name = main}
-- ::52.984186+ MJ_iOS_Test[:] 执行任务3-----<NSThread: 0x600000320940>{number = , name = (null)}
-- ::52.984453+ MJ_iOS_Test[:] 执行任务1-----<NSThread: 0x600000356840>{number = , name = main}
-- ::52.984710+ MJ_iOS_Test[:] 执行任务3-----<NSThread: 0x600000320940>{number = , name = (null)}
-- ::52.984928+ MJ_iOS_Test[:] 执行任务1-----<NSThread: 0x600000356840>{number = , name = main}
-- ::52.985130+ MJ_iOS_Test[:] 执行任务3-----<NSThread: 0x600000320940>{number = , name = (null)}
-- ::52.994169+ MJ_iOS_Test[:] 执行任务1-----<NSThread: 0x600000356840>{number = , name = main}
-- ::52.994181+ MJ_iOS_Test[:] 执行任务3-----<NSThread: 0x600000320940>{number = , name = (null)}
-- ::52.994355+ MJ_iOS_Test[:] 执行任务3------<NSThread: 0x600000320940>{number = , name = (null)}
-- ::52.994502+ MJ_iOS_Test[:] 执行任务3------<NSThread: 0x600000320940>{number = , name = (null)}
-- ::52.994671+ MJ_iOS_Test[:] 执行任务3------<NSThread: 0x600000320940>{number = , name = (null)}
-- ::52.994804+ MJ_iOS_Test[:] 执行任务3------<NSThread: 0x600000320940>{number = , name = (null)}
-- ::52.995173+ MJ_iOS_Test[:] 执行任务3------<NSThread: 0x600000320940>{number = , name = (null)}
-- ::52.995663+ MJ_iOS_Test[:] 执行任务3------<NSThread: 0x600000320940>{number = , name = (null)}
-- ::52.996280+ MJ_iOS_Test[:] 执行任务3------<NSThread: 0x600000320940>{number = , name = (null)}
-- ::52.996518+ MJ_iOS_Test[:] 执行任务3------<NSThread: 0x600000320940>{number = , name = (null)}
-- ::52.996819+ MJ_iOS_Test[:] 执行任务3------<NSThread: 0x600000320940>{number = , name = (null)}
-- ::52.997497+ MJ_iOS_Test[:] 执行任务3------<NSThread: 0x600000320940>{number = , name = (null)}
dispatch_queue_t queue2 = dispatch_get_global_queue(, ); dispatch_async(queue2, ^{
for (int i = ; i < ; i++) {
NSLog(@"执行任务3-----%@", [NSThread currentThread]);
}
}); dispatch_async(queue2, ^{
for (int i = ; i < ; i++) {
NSLog(@"执行任务3-2-----%@", [NSThread currentThread]);
}
}); for (int i = ; i < ; i++) {
NSLog(@"执行任务1-----%@", [NSThread currentThread]);
}
//打印
-- ::55.818176+ MJ_iOS_Test[:] 执行任务1-----<NSThread: 0x600002ed1180>{number = , name = main}
-- ::55.818227+ MJ_iOS_Test[:] 执行任务3------<NSThread: 0x600002eb23c0>{number = , name = (null)}
-- ::55.818227+ MJ_iOS_Test[:] 执行任务3-----<NSThread: 0x600002eb2380>{number = , name = (null)}
-- ::55.818495+ MJ_iOS_Test[:] 执行任务3-----<NSThread: 0x600002eb2380>{number = , name = (null)}
-- ::55.818500+ MJ_iOS_Test[:] 执行任务1-----<NSThread: 0x600002ed1180>{number = , name = main}
-- ::55.818500+ MJ_iOS_Test[:] 执行任务3------<NSThread: 0x600002eb23c0>{number = , name = (null)}
-- ::55.818630+ MJ_iOS_Test[:] 执行任务3-----<NSThread: 0x600002eb2380>{number = , name = (null)}
-- ::55.818657+ MJ_iOS_Test[:] 执行任务1-----<NSThread: 0x600002ed1180>{number = , name = main}
-- ::55.818753+ MJ_iOS_Test[:] 执行任务3------<NSThread: 0x600002eb23c0>{number = , name = (null)}
-- ::55.818758+ MJ_iOS_Test[:] 执行任务3-----<NSThread: 0x600002eb2380>{number = , name = (null)}
-- ::55.819027+ MJ_iOS_Test[:] 执行任务1-----<NSThread: 0x600002ed1180>{number = , name = main}
-- ::55.819361+ MJ_iOS_Test[:] 执行任务3------<NSThread: 0x600002eb23c0>{number = , name = (null)}
-- ::55.819644+ MJ_iOS_Test[:] 执行任务3-----<NSThread: 0x600002eb2380>{number = , name = (null)}
-- ::55.820062+ MJ_iOS_Test[:] 执行任务1-----<NSThread: 0x600002ed1180>{number = , name = main}
-- ::55.820389+ MJ_iOS_Test[:] 执行任务3------<NSThread: 0x600002eb23c0>{number = , name = (null)}
-- ::55.820744+ MJ_iOS_Test[:] 执行任务3-----<NSThread: 0x600002eb2380>{number = , name = (null)}
-- ::55.821125+ MJ_iOS_Test[:] 执行任务1-----<NSThread: 0x600002ed1180>{number = , name = main}
-- ::55.821634+ MJ_iOS_Test[:] 执行任务3------<NSThread: 0x600002eb23c0>{number = , name = -- ::55.822389+ MJ_iOS_Test[:] 执行任务1-----<NSThread: 0x600002ed1180>{number = , name = main}
(null)}
-- ::55.821989+ MJ_iOS_Test[:] 执行任务3-----<NSThread: 0x600002eb2380>{number = , name = (null)}
-- ::55.833276+ MJ_iOS_Test[:] 执行任务1-----<NSThread: 0x600002ed1180>{number = , name = main}
-- ::55.833308+ MJ_iOS_Test[:] 执行任务3-----<NSThread: 0x600002eb2380>{number = , name = (null)}
-- ::55.833282+ MJ_iOS_Test[:] 执行任务3------<NSThread: 0x600002eb23c0>{number = , name = (null)}
-- ::55.833419+ MJ_iOS_Test[:] 执行任务1-----<NSThread: 0x600002ed1180>{number = , name = main}
-- ::55.833462+ MJ_iOS_Test[:] 执行任务3-----<NSThread: 0x600002eb2380>{number = , name = (null)}
-- ::55.833503+ MJ_iOS_Test[:] 执行任务3------<NSThread: 0x600002eb23c0>{number = , name = (null)}
-- ::55.833543+ MJ_iOS_Test[:] 执行任务1-----<NSThread: 0x600002ed1180>{number = , name = main}
-- ::55.833890+ MJ_iOS_Test[:] 执行任务3-----<NSThread: 0x600002eb2380>{number = , name = (null)}
-- ::55.834534+ MJ_iOS_Test[:] 执行任务3------<NSThread: 0x600002eb23c0>{number = , name = (null)}
-- ::55.835481+ MJ_iOS_Test[:] 执行任务3------<NSThread: 0x600002eb23c0>{number = , name = (null)}
GCD死锁,及同步、异步、串行和并行队列组合情形的更多相关文章
- GCD的同步异步串行并行、NSOperation和NSOperationQueue一级用dispatch_once实现单例
转:http://www.tuicool.com/articles/NVVnMn (1)GCD实现的同步异步.串行并行. ——同步sync应用场景:用户登录,利用阻塞 ——串行异步应用场景:下载等耗时 ...
- 【iOS开发-91】GCD的同步异步串行并行、NSOperation和NSOperationQueue一级用dispatch_once实现单例
(1)GCD实现的同步异步.串行并行. --同步sync应用场景:用户登录,利用堵塞 --串行异步应用场景:下载等耗时间的任务 /** * 由于是异步.所以开通了子线程.可是由于是串行队列,所以仅仅须 ...
- iOS多线程——同步异步串行并行
串行并行异步同步的概念很容易让人混淆,关于这几个概念我在第一篇GCD中有解释,但是还不够清晰,所以这里重写一篇博客专门对这几个概念进行区分: 先说一下队列和任务: (1)队列分为串行和并行,任务的执行 ...
- GCD同步异步 串行并行大解析
/** 核心概念 任务:block里需要执行的操作 队列:把任务添加进入队列中,按照先进先出的原则来执行任务 串行队列:一个一个的执行 并行队列:可以让多个任务并发(同时)执行(自动开启多个线程同时 ...
- GCD中的dispatch_sync、dispatch_sync 分别与串行、并行队列组合执行小实验
平常开发中会经常用gcd做一下多线程任务,但一直没有对同步.异步任务在串行.并行队列的执行情况做个全面的认识,今天写了个demo跑了下,还是有些新发现的. 代码如下: - (void)touchesB ...
- iOS 之GCD串行和并发队列的理解
dispatch_queue_t serialQueue = dispatch_queue_create("com.lai.www", DISPATCH_QUEUE_SERIAL) ...
- python 同步异步,并发并行,同步锁
并发:系统具有处理多个任务(动作)的能力 并行:系统具有同时处理多个任务(动作)的能力 同步:当进程执行到一个IO(等待外部数据)的时候,需要等待,等待即同步 异步:当进程执行到一个IO(等待外部数据 ...
- IOS多线程知识总结/队列概念/GCD/主队列/并行队列/全局队列/主队列/串行队列/同步任务/异步任务区别(附代码)
进程:正在进行中的程序被称为进程,负责程序运行的内存分配;每一个进程都有自己独立的虚拟内存空间 线程:线程是进程中一个独立的执行路径(控制单元);一个进程中至少包含一条线程,即主线程 队列 dispa ...
- 【原】iOS多线程之异步任务+并行队列情况与异步任务+串行队列(主队列)情况
异步任务+并行队列 把异步任务放到并行队列进行执行,异步任务会在不同的线程中执行. /*异步执行+并行队列*/ - (IBAction)clickBasic1:(UIButton *)sender { ...
随机推荐
- 各浏览器禁用某网站JS脚本的方法 【转】
某些网站,经常会加载一些非常讨厌的JS脚本,如果我们想禁止这个网站的JS脚本,可以使用下面的方法: 一.IE浏览器 1.在Internet选项中,选择安全选项卡,然后点击受限制的站点,点击下面的站点 ...
- LeetCode 527---Word Abbreviation
527. Word Abbreviation Given an array of n distinct non-empty strings, you need to generate minimal ...
- Java volatile关键字解惑
volatile特性 内存可见性:通俗来说就是,线程A对一个volatile变量的修改,对于其它线程来说是可见的,即线程每次获取volatile变量的值都是最新的. volatile的使用场景 通过关 ...
- windows 设置CapsLock键开启大写后使用shift键取消大写
1.打开控制面板——>时钟.语言和区域——>更改键盘或其它输入法——>更改键盘——>高级键设置——>要关闭Caps Lock 2.ok
- Pig limit用法举例
lmt = limit data 10; 只获取指定条数的数据,不能保证每次得到的结果一致,先执行order再limit可以保证一致. 输入数据全部载入. 会触发reduce阶段 a ...
- Storm默认配置 default.yaml
default.yaml文件所在位置:apache-storm-0.9.4.tar.gz/apache-storm-0.9.4/lib/storm-core-0.94.jar/default.yaml ...
- Oracle EBS 隐藏帮助-诊断-检查
- 一些简单的SQL Server服务器监控
1:磁盘活动的一些监控 指标 吞吐量:IOPS,存储子系统每秒能提供多少次I/O 吞吐量,MB/S,I/O子系统每秒能提供多少MB 延时:每个I/O请求占用多少时间 队列长度:队列中有多少IO请求在等 ...
- [翻译] ios-image-filters
ios-image-filters https://github.com/esilverberg/ios-image-filters photoshop-style filter interface ...
- 全自动LTI部署OS
全自动LTI部署OS:零.通过ADK制作WinPE(需包含有imagex.exe工具,用来捕获映像)一.使用WinPE中的imagex捕获映像(install.wim)二.使用MDT制作启动映像(bo ...