美文网首页
iOS开发-多线程的简单认识

iOS开发-多线程的简单认识

作者: 黄泉殇 | 来源:发表于2016-07-21 22:08 被阅读0次

    // 当我们应用程序刚刚运行的时候 系统会自动为我们开放一个线程,这个线程叫做主线程
    // 子线程:程序员用代码手动开启的线程
    // 线程存在的意义:执行耗时操作的任务
    // 子线程在执行完自己的任务之后会自动销毁

    NSThread

    - (void)creatNSThread
    {
        // 创建一个线程
        NSThread *thread = [[NSThread alloc] initWithTarget:self selector:@selector(haoshicaozuo) object:@"abc"];
        thread.name = @"123";
        [thread start];
    //    NSLog(@"%@", thread);
        // 当前应用程序的主线程
        NSLog(@"%@", [NSThread mainThread]);
        // 当前线程
        NSLog(@"%@", [NSThread currentThread]);
        // 判断是否为主线程
        NSLog(@"%d", [NSThread isMainThread]);
    }
    
    - (void)haoshicaozuo
    {
        // 当前应用程序的主线程
        NSLog(@"%@", [NSThread mainThread]);
        // 当前线程
        NSLog(@"%@", [NSThread currentThread]);
        // 判断是否为主线程
        NSLog(@"%d", [NSThread isMainThread]);
    }
    
    - (void)creatNSThread1
    {
        // 快捷创建 无返回值
        [NSThread detachNewThreadSelector:@selector(haoshicaozuo) toTarget:self withObject:@"456"];
    }
    
    - (void)creatNSThread2
    {
        // 隐式开启线程
        [self performSelectorInBackground:@selector(haoshicaozuo) withObject:@"789"];
    }
    

    NSOperation

    // NSOperation 是一个抽象类,我们一般不直接使用它,而是使用它的子类NSInvocationOperation 类 还有NSBlockOperation
    // 如果他们单独使用都是在主线程执行,只有和队列一起使用才是在子线程下执行的

    - (void)creatNSOperation
    {
        NSInvocationOperation *operation1 = [[NSInvocationOperation alloc] initWithTarget:self selector:@selector(operationAction1) object:nil];
        
        NSInvocationOperation *operation2 = [[NSInvocationOperation alloc] initWithTarget:self selector:@selector(operationAction2) object:nil];
        
        NSBlockOperation *operation3 = [NSBlockOperation blockOperationWithBlock:^{
            for (int i = 20; i < 30; i++) {
                NSLog(@"%d", i);
            }
        }];
        
        // 操作队列
        // 目的:是将我们的任务放在一个队列中执行
        // 任务:任务执行在主线程还是在子线程全都是由我们的队列来决定的
        
        // 加入到队列
        // mainQueue 代表着主队列
        // 如果是alloc init 的 那就代表着其他队列
    //    NSOperationQueue *queue = [NSOperationQueue mainQueue];
        NSOperationQueue *queue = [[NSOperationQueue alloc] init];
        // 先加的先执行,后加的后执行,但是执行的时间不一定,后执行的可能先执行完
        [queue addOperation:operation1];
        [queue addOperation:operation2];
        [queue addOperation:operation3];
    }
    
    - (void)operationAction1
    {
        for (int i = 0; i < 10; i++) {
            NSLog(@"%d", i);
        }
    }
    
    - (void)operationAction2
    {
        for (int i = 10; i < 20; i++) {
            NSLog(@"%d", i);
        }
    }
    

    GCD

    // 异步:不在一个线程执行
    // 同步:在同一个线程从下往下执行
    // 串行:串在一起执行
    // 并行:一起执行

    同步 + 主队列
    - (void)creatSyncMain
    {
        // 获得主队列(主队列也是一个串行队列)
        dispatch_queue_t queue = dispatch_get_main_queue();
        // 将任务加到队列中
        // 第一个参数: 队列
        // 第二个参数: 要执行的任务
        dispatch_sync(queue, ^{
            NSLog(@"1--------%@", [NSThread currentThread]);
        });
        
        dispatch_sync(queue, ^{
            NSLog(@"2--------%@", [NSThread currentThread]);
        });
    
        dispatch_sync(queue, ^{
            NSLog(@"3--------%@", [NSThread currentThread]);
        });
    
    }
    
    异步 + 主队列:不开辟线程,就在主线程执行
    - (void)creatAsyncMain
    {
        // 获得主队列(主队列也是一个串行队列)
        dispatch_queue_t queue = dispatch_get_main_queue();
        // 将任务加到队列中
        // 第一个参数: 队列
        // 第二个参数: 要执行的任务
        dispatch_async(queue, ^{
            NSLog(@"1--------%@", [NSThread currentThread]);
        });
        
        dispatch_async(queue, ^{
            NSLog(@"2--------%@", [NSThread currentThread]);
        });
        
        dispatch_async(queue, ^{
            NSLog(@"3--------%@", [NSThread currentThread]);
        });
        
    }
    
    同步 + 串行队列:不具备开启线程的能力,在当前线程完成任务
    - (void)creatSyncSerial
    {
        // 创建串行队列
        // 第一个参数 队列的参数
        // 第二个参数 类型 DISPATCH_QUEUE_SERIAL 为串行队列
        dispatch_queue_t queue = dispatch_queue_create("aaa.com.queue", DISPATCH_QUEUE_SERIAL);
        dispatch_sync(queue, ^{
            NSLog(@"1--------%@", [NSThread currentThread]);
        });
        
        dispatch_sync(queue, ^{
            NSLog(@"2--------%@", [NSThread currentThread]);
        });
    
        dispatch_sync(queue, ^{
            NSLog(@"3--------%@", [NSThread currentThread]);
        });
    
    }
    
    异步 + 串行队列:具备开启线程的能力,但是任务是串行的,执行完一个才会去执行下一个
    - (void)creatAsyncSerial
    {
        dispatch_queue_t queue = dispatch_queue_create("aaa", DISPATCH_QUEUE_SERIAL);
        dispatch_async(queue, ^{
            NSLog(@"1--------%@", [NSThread currentThread]);
        });
        
        dispatch_async(queue, ^{
            NSLog(@"2--------%@", [NSThread currentThread]);
        });
    
        dispatch_async(queue, ^{
            NSLog(@"3--------%@", [NSThread currentThread]);
        });
    
    }
    
    同步 + 并发队列:不具备开启线程的能力,在主队列并发的功能也就没用了
    - (void)creatSyncConcurrent
    {
        // DISPATCH_QUEUE_CONCURRENT为并发队列
        // 我们自己创建的并发队列 一般不用
    //    dispatch_queue_t queue = dispatch_queue_create("bbb", DISPATCH_QUEUE_CONCURRENT);
        // 创建一个并发队列
        // 获得全局的并发队列
        // 第一个参数为一个优先级 默认的就行
        dispatch_queue_t queue = dispatch_get_global_queue(DISPATCH_QUEUE_PRIORITY_DEFAULT, 0);
        dispatch_sync(queue, ^{
            NSLog(@"1--------%@", [NSThread currentThread]);
        });
        
        dispatch_sync(queue, ^{
            NSLog(@"2--------%@", [NSThread currentThread]);
        });
        
        dispatch_sync(queue, ^{
            NSLog(@"3--------%@", [NSThread currentThread]);
        });
    }
    
    异步 + 并发队列:异步具备开启子线程的能力,并且并发执行任务,多线程一般就是用这个
    - (void)creatAsyncConcurrent
    {
        dispatch_queue_t queue = dispatch_get_global_queue(DISPATCH_QUEUE_PRIORITY_DEFAULT, 0);
        dispatch_async(queue, ^{
            NSLog(@"1--------%@", [NSThread currentThread]);
        });
        
        dispatch_async(queue, ^{
            NSLog(@"2--------%@", [NSThread currentThread]);
        });
        
        dispatch_async(queue, ^{
            NSLog(@"3--------%@", [NSThread currentThread]);
        });
    }
    

    GCD的简单函数使用

    延迟执行
    - (void)creatAfter
    {
        dispatch_after(dispatch_time(DISPATCH_TIME_NOW, (int64_t)(5 * NSEC_PER_SEC)), dispatch_get_main_queue(), ^{
            NSLog(@"%@", [NSThread currentThread]);
            NSLog(@"666");
        });
    }
    
    快速遍历
    - (void)rapidTraverse
    {
        for (int i = 0; i < 100; i++) {
            NSLog(@"%d", i);
        }
        dispatch_queue_t queue = dispatch_get_global_queue(DISPATCH_QUEUE_PRIORITY_DEFAULT, 0);
        dispatch_apply(100, queue, ^(size_t index) {
            NSLog(@"%zd %@", index, [NSThread currentThread]);
        });
    }
    
    组队列
    - (void)creatGroup
    {
        // 获取一个并发队列
        dispatch_queue_t queue = dispatch_get_global_queue(DISPATCH_QUEUE_PRIORITY_DEFAULT, 0);
        // 创建一个组队列
        dispatch_group_t group = dispatch_group_create();
        // 下载图片1
        dispatch_group_async(group, queue, ^{
            NSURL *url = [NSURL URLWithString:@"https://ss0.bdstatic.com/94oJfD_bAAcT8t7mm9GUKT-xh_/timg?image&quality=100&size=b4000_4000&sec=1464231860&di=33256b2f206f8082ad634b5250a2b39d&src=http://www.benbenla.cn/images/20120330/benbenla-04b.jpg"];
            NSData *data = [NSData dataWithContentsOfURL:url];
            self.image1 = [UIImage imageWithData:data];
        });
        dispatch_group_async(group, queue, ^{
            NSURL *url = [NSURL URLWithString:@"http://www.deskcar.com/desktop/fengjing/200895150214/21.jpg"];
            NSData *data = [NSData dataWithContentsOfURL:url];
            self.image2 = [UIImage imageWithData:data];
        });
    
        // 将图片1和图片2拼接在一起
        dispatch_group_notify(group, queue, ^{
            // 开启一个新的图片上下文
            UIGraphicsBeginImageContext(CGSizeMake(300, 300));
            // 绘制图片
            [self.image1 drawInRect:CGRectMake(0, 0, 150, 300)];
            [self.image2 drawInRect:CGRectMake(150, 0, 150, 300)];
            // 取得图片上下文中的图片
            UIImage *image = UIGraphicsGetImageFromCurrentImageContext();
            // 结束图片上下文
            UIGraphicsEndImageContext();
            dispatch_async(dispatch_get_main_queue(), ^{
                self.imgView.image = image;
            });
        });
        
    }
    

    相关文章

      网友评论

          本文标题:iOS开发-多线程的简单认识

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