zoukankan      html  css  js  c++  java
  • GCD的相关函数使用

    GCD

    是iOS多线程实现方案之一,非常常用

    英文翻译过来就是伟大的中枢调度器,也有人戏称为是牛逼的中枢调度器

    是苹果公司为多核的并行运算提出的解决方案

    1.一次性函数

    dispatch_once

    顾名思义是只执行一次的函数,注意是整个程序中只执行一次(单例模式常用到)

    - (void)once {
        
        //一次性函数,只执行函数
        static dispatch_once_t onceToken;
        dispatch_once(&onceToken, ^{
            //里面默认线程安全的
            NSLog(@"------run");
        });
    }

    2.栅栏函数

    dispatch_barrier_async

    作用就是控制多线程的执行顺序

    - (void)barrier {
        dispatch_queue_t queue = dispatch_queue_create("123", DISPATCH_QUEUE_CONCURRENT);
        
        dispatch_async(queue, ^{
            NSLog(@"_______1--------%@",[NSThread currentThread]);
        });
        dispatch_async(queue, ^{
            NSLog(@"_______2--------%@",[NSThread currentThread]);
        });
        
        //像栅栏一样,让上面的先执行完,再执行下面的
        dispatch_barrier_async(queue, ^{
            NSLog(@"----barrier-----%@",[NSThread currentThread]);
        });
        
        dispatch_async(queue, ^{
            NSLog(@"_______3--------%@",[NSThread currentThread]);
        });
        dispatch_async(queue, ^{
            NSLog(@"_______4--------%@",[NSThread currentThread]);
        });
        
    }

    3.快速迭代函数

    dispatch_apply

    作用就是开启多个线程同时完成某一件事,例如同时下载多张图片

    //一般的做法
    - (void)cutFromFileTo {
        //一般在子线程中做
        //创建并行队列
        dispatch_queue_t queue = dispatch_get_global_queue(DISPATCH_QUEUE_PRIORITY_DEFAULT, 0);
        dispatch_async(queue, ^{
            //起始路径
            NSString *from = @"/Users/DDZ/Desktop/From";
            //目标路径
            NSString *to = @"/Users/DDZ/Desktop/To";
            
            
            NSFileManager *mgr = [NSFileManager defaultManager];
            //获取起始路径中所有文件路径
            NSArray *subpaths = [mgr subpathsAtPath:from];
            
            for (int i = 0; i < subpaths.count; i++) {
                
                //将路径字符串进行拼接
                NSString *fromFullPath = [NSString stringWithFormat:@"%@/%@",from,subpaths[i]];
                NSString *toFullPath = [NSString stringWithFormat:@"%@/%@",to,subpaths[i]];
                
                
                [mgr moveItemAtPath:fromFullPath toPath:toFullPath error:nil];
                
            }
            NSLog(@"剪切成功");
            
        });
    }
    View Code
    //使用快速迭代进行剪切
    - (void)cutFileApply {
        //起始路径
        NSString *from = @"/Users/DDZ/Desktop/From";
        //目标路径
        NSString *to = @"/Users/DDZ/Desktop/To";
        
        
        NSFileManager *mgr = [NSFileManager defaultManager];
        //获取起始路径中所有文件路径
        NSArray *subpaths = [mgr subpathsAtPath:from];
        
        
        dispatch_apply(subpaths.count, dispatch_get_global_queue(DISPATCH_QUEUE_PRIORITY_DEFAULT, 0), ^(size_t index) {
            
            NSString *subpath = subpaths[index];
            //将路径字符串进行拼接
            NSString *fromFullPath = [NSString stringWithFormat:@"%@/%@",from,subpath];
            NSString *toFullPath = [NSString stringWithFormat:@"%@/%@",to,subpath];
            
            //剪切
            [mgr moveItemAtPath:fromFullPath toPath:toFullPath error:nil];
    
        });
        
    }

    一般的方法只能一张图片剪切完之后,再进行下一张得剪切

    而使用快速迭代则可以同时进行剪切。

    4.队列组

    dispatch_group_async

    与栅栏函数有相同的目的,为了控制多线程的执行顺序

    例如下载两张图片之后,再将这两者合并成新的图片并显示。

    必须得先下完之后才能合并吧!(顺序问题,多线程是不可控的)

    //队列组
    - (void)group {
        
        //创建组
        dispatch_group_t group = dispatch_group_create();
        
        dispatch_queue_t queue = dispatch_get_global_queue(DISPATCH_QUEUE_PRIORITY_DEFAULT, 0);
        
        //1.下载图片1
        dispatch_group_async(group, queue, ^{
            
            //实现下载
            NSURL *url = [NSURL URLWithString:@"http://g.hiphotos.baidu.com/image/pic/item/6c224f4a20a446230761b9b79c22720e0df3d7bf.jpg"];
            NSData *data = [NSData dataWithContentsOfURL:url];
            //生成图片
            self.img1 = [UIImage imageWithData:data];
            
        });
        
        //2.下载图片2
        dispatch_group_async(group, queue, ^{
            
            //实现下载
            NSURL *url = [NSURL URLWithString:@"http://h.hiphotos.baidu.com/image/pic/item/b812c8fcc3cec3fd5b9db074d488d43f8794270b.jpg"];
            NSData *data = [NSData dataWithContentsOfURL:url];
            self.img2 = [UIImage imageWithData:data];
            
        });
        
        //3.将图片1,图片2合成一张新的图片
        dispatch_group_notify(group, queue, ^{
            //开启新的图形上下文
            UIGraphicsBeginImageContext(CGSizeMake(200, 200));
            
            //绘制图片
            [self.img1 drawInRect:CGRectMake(0, 0, 100, 200)];
            
            [self.img2 drawInRect:CGRectMake(100, 0, 100, 200)];
            
            //取得上下文中的图片
            UIImage *image = UIGraphicsGetImageFromCurrentImageContext();
            
            //结束上下文
            UIGraphicsEndImageContext();
            
            //回到主线程显示图片
            dispatch_async(dispatch_get_main_queue(), ^{
                //4.将新图片显示出来
                
                self.imageView.image = image;
            });
            
        });
        
    
    }
    View Code

    5.延时(补充)

    - (void)delay {
        //延时
        NSLog(@"______");
        [self performSelector:@selector(run) withObject:nil afterDelay:2.0];
    }
    
    - (void)run {
        NSLog(@"end");
    }
  • 相关阅读:
    上一张作业day16
    python 函数递归,三元表达式解读,匿名一次性函数,模块略解
    迭代器,生成器与内置函数
    闭合函数和装饰器
    函数的其他关键点*与**,函数的对象可以当做变量去使用,函数的嵌套,名称空间
    python函数,应用与讲解
    文件处理方式
    html-04 html骨架
    html-03 Web标准
    html-02 浏览器内核
  • 原文地址:https://www.cnblogs.com/langji/p/5321977.html
Copyright © 2011-2022 走看看