美文网首页
多线程相关

多线程相关

作者: 萝卜丝巾 | 来源:发表于2020-08-12 11:50 被阅读0次


    引文:


    1. GCD

    2. NSOperation

    3. NSThread

    4. 多线程与锁



    注意: 在主线程中执行同步任务将发生死锁

    死锁原因

    系统在主队列开启主线程执行任务,用户手动添加一个同步任务到当当前线程中,由于同步任务不开辟额外的线程去处理,所以就在当前线程中去执行任务,由于当前线程是主线程,所有就造成任务的相互等待过程从而产生死锁.

    image.png
    同步串行
    image.png

    思考: 输出什么?

     - (void)viewDidLoad {
        [super viewDidLoad];
        dispatch_async(dispatch_get_global_queue(DISPATCH_QUEUE_PRIORITY_DEFAULT, 0), ^{  
          NSLog(@"1");
          [self performSelector:@selector(test) withObject:self afterDelay:2];
          NSLog(@"2");  });
      }
     - (void)test{
          NSLog(@"test");
      }
    

    输出: 1 2

    不会输出test.

    因为performSelector方法要添加到对应线程的runloop之后才会生效,由于异步任务是在dispatch_get_global_queue并发队列中的, 默认不开启runloop,所有不会执行.

    如果是添加到主队列中,就会执行了.


    Dispathc_barrier_async() (栅栏模式)

    可以实现多读单写.

    image.png
    Dispatch_group_async() (组别模式)

    可以实现多任务执行完毕后统一处理后续业务逻辑

    image.png
    NSOperation

    需要和NSOperationQueue配合使用来实现多线程方案

    特点:

    1. 添加任务依赖
    2. 认为执行状态控制
      1. isReady --> 准备

      2. isExecuting --> 执行

      3. isFinished --> 完成

      4. isCancelled --> 取消

      如果只重写main方法,底层控制变更任务执行状态,以及任务的退出
      如果重写了start方法, 自行控制任务的执行状态

    3. 设置最大并发量


    @synchronized

    一般创建单例对象使用


    atomic

    修饰属性的关键字

    对被修饰对象进行原子操作(不负责使用)

         @property (atomic) NSMutableArray *arr;
         self.arr = [NSMutableArray array]; //✔️ 
         [self.arr addObject:@"1"];  // ❎ 不负责使用
    

    自旋锁(OSSpinLock)

    循环等待询问,不释放当前资源.

    用于轻量级数据访问


    NSLock
    
    - (void)test{
          NSLock *lock = [[NSLock alloc] init];
          [lock lock];
          [self test2];
          [lock unlock];
      }
    
    - (void)test2{
          NSLock *lock = [[NSLock alloc] init];
          [lock lock];
          [self test3];
          [lock unlock];
      }
    

    会造成死锁 ,解决方案是使用递归锁


    递归锁 (NSRecureiveLock)

    可以无限重入

    - (void)test{
      NSRecursiveLock *lock = [[NSRecursiveLock alloc] init];
        [lock lock];
        [self test2];
        [lock unlock];
      }
    - (void)test2{
      NSRecursiveLock *lock = [[NSRecursiveLock alloc] init];
        [lock lock];
        // 业务逻辑
        [lock unlock];
      }
    

    GCD信号量(dispatch_semaphore_t)

    参考文献吧

    相关文章

      网友评论

          本文标题:多线程相关

          本文链接:https://www.haomeiwen.com/subject/mqppdktx.html