IOS中的多线程之GCD

Posted

tags:

篇首语:本文由小常识网(cha138.com)小编为大家整理,主要介绍了IOS中的多线程之GCD相关的知识,希望对你有一定的参考价值。

  在ios中,使用多线程有三种方式,分别是:NSThread、NSOperation和NSOperationQueue、GCD,在本节,主要讲解一下CDD的使用。

  GCD(Grand Central Dispatch) ,他是基于C语言开发的一套多线程开发机制,也是目前苹果官方推荐的多线程开发方法。GCD的抽象层次最高,用起来比较简单,但是因为它是基于C语言开发的,是面向过程的,所以在使用的时候不如面向对象的好理解。但是GCD这种机制相比较于前面两种多线程开发方式最显著的优点就是它对于多核运算更加有效。

GCD队列

  GCD中也有一个类似于NSOperationQueue的队列,GCD统一管理整个队列中的任务,GCD中的队列分为三种:

(1)     串行队列 dispatch_queue_create(, ):只有一个线程,加入到队列中的操作按添加顺序依次执行。

(2)     全局队列dispatch_get_global_queue(,):有多个线程,操作进来之后它会将这些队列安排在可用的处理器上,同时保证先进来的任务优先处理。

(3)     主队列 dispatch_get_main_queue():用来执行主线程上的操作任务。

GCD使用

  从网络加载图片会使用多线程的方式,在这里,使用GCD的方式从网络获取图片。

  使用GCD取数据的时候有同步dispatch_sync(,)和异步dispatch_async(,)两种方式,一般会选择使用异步的方式请求数据。

  此外,如果是一组图片,可以选择使用串行队列请求显示,也就是按照顺序依次显示;还可以使用全局队列请求显示,显示的时候是异步并发,不按顺序随机显示。在下面的代码中,分别介绍一下两种方式。

代码

//  ViewController.m
//  GCD_Demo
//
//  Created by jerei on 15-11-13.
//  Copyright (c) 2015年 jerehedu. All rights reserved.
//

#import "ViewController.h"
#define IMG_VIEW_WIDTH 90
#define IMG_VIEW_HEIGHT 45
#define GAP (([UIScreen mainScreen].bounds.size.width - (2*IMG_VIEW_WIDTH))/3.0)

@interface ViewController ()

@end

@implementation ViewController

- (void)viewDidLoad {
    [super viewDidLoad];
 
    //设置界面上显示图片的imageView
    [self addImageViews];
    
    //加按钮
    [self addBtns];
}

#pragma mark - 设置界面上显示图片的imageView
-(void)addImageViews{
    
    for (int i=0; i<10; i++) {
        UIImageView *imgView = [[UIImageView alloc] initWithFrame:CGRectMake(GAP+(i%2)*(IMG_VIEW_WIDTH+GAP), 60 + GAP + (i/2)*(IMG_VIEW_HEIGHT+20), IMG_VIEW_WIDTH, IMG_VIEW_HEIGHT)];
        imgView.tag = i+1;
        imgView.backgroundColor = [UIColor redColor];
        [self.view addSubview:imgView];
    }
}

#pragma mark - 按钮
-(void)addBtns{
    UIButton *serial_btn = [[UIButton alloc] initWithFrame:CGRectMake(GAP, 30, IMG_VIEW_WIDTH, IMG_VIEW_HEIGHT)];
    [serial_btn setTitle:@"串行加载" forState:UIControlStateNormal];
    [serial_btn setBackgroundColor:[UIColor purpleColor]];
    [self.view addSubview:serial_btn];
    [serial_btn addTarget:self action:@selector(loadImage_gcd_serial) forControlEvents:UIControlEventTouchUpInside];
    
    UIButton *global_btn = [[UIButton alloc] initWithFrame:CGRectMake(2*GAP+IMG_VIEW_WIDTH, 30, IMG_VIEW_WIDTH, IMG_VIEW_HEIGHT)];
    [global_btn setTitle:@"并行加载" forState:UIControlStateNormal];
    [global_btn setBackgroundColor:[UIColor purpleColor]];
    [self.view addSubview:global_btn];
    [global_btn addTarget:self action:@selector(loadImage_gcd_global) forControlEvents:UIControlEventTouchUpInside];
}

#pragma mark - 从网络串行加载照片
-(void)loadImage_gcd_serial{
    //串行队列
    dispatch_queue_t serialQueue = dispatch_queue_create("myThreadQueue1", DISPATCH_QUEUE_SERIAL);
    
    //请求图片
    for (int i=0; i<10; i++) {
        dispatch_async(serialQueue, ^{
            //从网络获取图片
            NSURL *url = [NSURL URLWithString:@"http://www.jerehedu.com/images/temp/logo.gif"];
            NSData *data = [NSData dataWithContentsOfURL:url];
            UIImage *image = [UIImage imageWithData:data];
            
            //回到主线程刷新界面
            dispatch_sync(dispatch_get_main_queue(), ^{
                UIImageView *currentImgView = (UIImageView *)[self.view viewWithTag:i+1];
                currentImgView.image = image;
            });
        });
    }
}

#pragma mark - 从网络并行加载照片
-(void)loadImage_gcd_global{
    //并行队列
    dispatch_queue_t globalQueue = dispatch_get_global_queue(DISPATCH_QUEUE_PRIORITY_DEFAULT, 0);
    
    //请求图片
    for (int i=0; i<10; i++) {
        dispatch_async(globalQueue, ^{
            //从网络获取图片
            NSURL *url = [NSURL URLWithString:@"http://www.jerehedu.com/images/temp/logo.gif"];
            NSData *data = [NSData dataWithContentsOfURL:url];
            UIImage *image = [UIImage imageWithData:data];
            
            //回到主线程刷新界面
            dispatch_sync(dispatch_get_main_queue(), ^{
                UIImageView *currentImgView = (UIImageView *)[self.view viewWithTag:i+1];
                currentImgView.image = image;
            });
        });
    }
}

- (void)didReceiveMemoryWarning {
    [super didReceiveMemoryWarning];
}

@end

 

作者:杰瑞教育
出处:http://www.cnblogs.com/jerehedu/ 
版权声明:本文版权归杰瑞教育技有限公司和博客园共有,欢迎转载,但未经作者同意必须保留此段声明,且在文章页面明显位置给出原文连接,否则保留追究法律责任的权利。
技术咨询:技术分享
 

以上是关于IOS中的多线程之GCD的主要内容,如果未能解决你的问题,请参考以下文章

Ios 多线程之NSOperation与NSOprationQueue

iOS开发:深入理解GCD 第二篇(dispatch_groupdispatch_barrier基于线程安全的多读单写)

Ios 多线程之NSOperation与NSOprationQueue

iOS之深入解析CFRunloop的多线程隐患

iOS底层探索之多线程—GCD不同队列源码分析

iOS 开发--多线程