多线程代码执行先后的顺序问题

  • 前言
    • 多线程代码执行先后的是怎样的呢?我认为执行代码的先后顺序最外层的dispatch_sync(同步)和dispatch_async(异步)。究竟是不是这样呢?就让我来做以下验证吧。

1、同步(串行/并行)队列

- (void)viewDidLoad {
    [super viewDidLoad];
    [self test];
}

/** 输出
 *  DISPATCH_QUEUE_CONCURRENT : 1 2 3 4 13 14 7 8 5 6
 
 *  DISPATCH_QUEUE_SERIAL: 1 2 3 4 13 14 7 8 5 6
 */
- (void)test{
    NSLog(@"ming -- 1");
    NSLog(@"ming -- 2");
//                                                              DISPATCH_QUEUE_SERIAL
    dispatch_queue_t queue = dispatch_queue_create("mingming2", DISPATCH_QUEUE_CONCURRENT);
    
    dispatch_sync(queue, ^{
        NSLog(@"ming -- 3");
        NSLog(@"ming -- 4");
        NSLog(@"ming -- 13");
        NSLog(@"ming -- 14");
        
        dispatch_async(dispatch_get_main_queue(), ^{
            NSLog(@"ming -- 5");
            [NSThread sleepForTimeInterval:5.0];
            NSLog(@"ming -- 6");
        });
        NSLog(@"ming -- 7");
    });
    NSLog(@"ming -- 8");
    NSLog(@"+=====+++++++++++++=============+++++++++++++++++++++++++====");
}
多线程代码执行先后的顺序问题_第1张图片
test结果.png

2、异步全局队列

- (void)viewDidLoad {
    [super viewDidLoad];
    [self test2];
}

/** 输出
 *  1 2 8 3 4 7 5 6
 */
- (void)test2{
    NSLog(@"ming -- 1");
    NSLog(@"ming -- 2");
    
    dispatch_async(dispatch_get_global_queue(0, 0), ^{
        NSLog(@"ming -- 3");
        NSLog(@"ming -- 4");
        
        dispatch_async(dispatch_get_main_queue(), ^{
            NSLog(@"ming -- 5");
            [NSThread sleepForTimeInterval:5.0];
            NSLog(@"ming -- 6");
        });
        NSLog(@"ming -- 7" );
    });
    NSLog(@"ming -- 8");
    NSLog(@"+=====+++++++++++++=============+++++++++++++++++++++++++====");
}```
![test2结果.png](http://upload-images.jianshu.io/upload_images/1429890-bf0b2987b5a79517.png?imageMogr2/auto-orient/strip%7CimageView2/2/w/1240)

- ####补充两张dispatch_async图片:
![](http://upload-images.jianshu.io/upload_images/1429890-15756ef5d314ee60.png?imageMogr2/auto-orient/strip%7CimageView2/2/w/1240)
![](http://upload-images.jianshu.io/upload_images/1429890-12d26162f53ba200.png?imageMogr2/auto-orient/strip%7CimageView2/2/w/1240)
![打印.png](http://upload-images.jianshu.io/upload_images/1429890-b0bbeb3204343b27.png?imageMogr2/auto-orient/strip%7CimageView2/2/w/1240)
- #####总结:异步同时执行,并没有明显的先后顺序之分。
***

#3、同步全局队列
  • (void)viewDidLoad {
    [super viewDidLoad];
    [self test3];
    }

/** 输出

  • 1 2 3 4 7 8 5 6
    */
  • (void)test3{
    NSLog(@"ming -- 1");
    NSLog(@"ming -- 2");

    dispatch_sync(dispatch_get_global_queue(0, 0), ^{
    NSLog(@"ming -- 3");
    NSLog(@"ming -- 4");

      dispatch_async(dispatch_get_main_queue(), ^{
          NSLog(@"ming -- 5");
          [NSThread sleepForTimeInterval:5.0];
          NSLog(@"ming -- 6");
      });
      NSLog(@"ming -- 7");
    

    });
    NSLog(@"ming -- 8");
    }

![test3结果.png](http://upload-images.jianshu.io/upload_images/1429890-2bf1cb883a1c1358.png?imageMogr2/auto-orient/strip%7CimageView2/2/w/1240)
***

#总结,通过三处代码。通过同步/异步、串行/并发(全局/主线程)的组合,可以看出,执行代码的先后顺序最外层的dispatch_sync(同步)和dispatch_async(异步)。
- `dispatch_sync(同步)——同步的话就按顺序执行,先执行最外层的dispatch_sync的代码,再执行NSLog(@"ming -- 8");,最后执行 dispatch_async(dispatch_get_main_queue(), ^{代码});里面的代码。`

- `dispatch_async(异步)——异步的话就不按顺序执行,先执行NSLog(@"ming -- 8");,再执行最外层的dispatch_async的代码,最后执行 dispatch_async(dispatch_get_main_queue(), ^{代码});里面的代码。`

- Tip
>值得注意的是dispatch_sync(同步)的时候,如果是
```dispatch_sync(dispatch_get_global_queue(0, 0), ^{
     dispatch_sync(dispatch_get_main_queue(), ^{});
}```
这种情况,在同步线程执行主队列,会造成死锁.如下图代码所示:

dispatch_sync(dispatch_get_global_queue(0, 0), ^{
NSLog(@"ming -- 3");

    dispatch_sync(dispatch_get_main_queue(), ^{
        NSLog(@"ming -- 5");
        [NSThread sleepForTimeInterval:5.0];
        NSLog(@"ming -- 6");
    });
    NSLog(@"ming -- 7");
});```

你可能感兴趣的:(多线程代码执行先后的顺序问题)