iOS 多線程學習筆記 —— GCD

本文複製、參考自文章:iOS多線程編程之Grand Central Dispatch(GCD)介紹和使用 ,主要爲了增強我的對知識的理解和記憶,不作他用。原做者聲明:html

著做權聲明:本文由http://blog.csdn.net/totogo2010/原創,歡迎轉載分享。請尊重做者勞動,轉載時保留該聲明和做者博客連接,謝謝!ios

這裏對原做者的辛勤工做表示感謝!數據庫

1. 簡介

GCD (Grand Central Dispatch) 是創建任務並行執行的線程池模式的基礎上的,以優化支持多核、多處理器系統。編程

GCD的工做原理是:讓程序平行排隊的特定任務,根據可用的處理資源,安排他們在任何可用的核心上執行任務。一個任務能夠是一個函數(function)或者是一個block。網絡

GCD的底層依然是用線程實現,不過沒必要關心實現細節。多線程

GCD的FIFO隊列稱爲 調度隊列(dispatch queue), 它能夠保證先來的先執行。dispatch 的、queue 分爲如下3種:併發

 (1) Serial (連續調度隊列)

 又稱爲 私有調度隊列(pirvate dispatch queue), 同時只執行一個任務。Serial queue一般用於同步訪問特定的資源或數據。當建立多個Serial queue時,雖然它們各自隊列內是單獨執行的,但隊列間是併發執行的。app

 (2) Concurrent (併發調度隊列)

 又稱爲 全局調度隊列(global dispatch queue), 能夠併發地執行隊列中的多個任務,可是執行完成的順序是隨機的。異步

 (3) Main dispatch queue(主調度隊列)

 它是全局可用的serial queue,是在應用程序主線程上執行任務的。async

2. 調度隊列的使用

2.1 經常使用的方法 dispatch_async

  爲了不界面在處理耗時的操做時卡死,好比讀取網絡數據、IO、數據庫讀寫等,咱們會在另外一個線程中去處理這些操做,而後通知主線程更新界面。

  用GCD實現這個流程比前面介紹的NSThread\NSOperation的方法都要簡單,代碼以下:

dispatch_async(dispatch_get_global_queue(DISPATCH_QUEUE_PRIORITY_DEFAULT, 0), ^{
        // 耗時的操做

  dispatch_async(dispatch_get_main_queue(), ^{
       // 更新界面
  });
});

針對以前圖片加載的示例:

- (void)viewDidLoad
{
    [super viewDidLoad];
    
    // Do any additional setup after loading the view, typically from a nib.
//    NSThread* thread = [[NSThread alloc] initWithTarget:self selector:@selector(downloadImage:) object:kURL];
//    [thread start];
    
    dispatch_async(dispatch_get_global_queue(DISPATCH_QUEUE_PRIORITY_DEFAULT, 0), ^{
        NSURL* url = [NSURL URLWithString:kURL];
        NSData* data = [[NSData alloc] initWithContentsOfURL:url];
        UIImage* image = [[UIImage alloc] initWithData:data];
        if (data != nil)
        {
            dispatch_async(dispatch_get_main_queue(), ^{
                self.imageView.image = image;
            });
        }
    });
    
    
}

GCD會自動根據任務在多核處理器上分配資源,優化程序。

系統給每一個應用程序提供了三個併發調度隊列(concurrent dispatch queues),這3個隊列是全局的,它們只有優先級的不一樣。由於是全局的,咱們不須要去建立,只須要經過使用函數  dispatch_get_global_queue 去獲得隊列。以下:

dispatch_queue_t globalQ = dispatch_get_global_queue(DISPATCH_QUEU_PRIORITY_DEFAULT, 0);

系統還提供了一個主調度隊列 main_queue

dispatch_queue_t mainQueue = dispatch_get_main_queue();

這些隊列都是全局隊列,,不用retain或release。

2.2 dispatch_group_async的使用

 dispatch_group_async能夠實現監聽一組任務是否完成,完成後再通知執行其餘的操做。以下示例:

    dispatch_queue_t queue = dispatch_get_global_queue(DISPATCH_QUEUE_PRIORITY_DEFAULT, 0);
    dispatch_group_t group = dispatch_group_create();
    
    dispatch_group_async(group, queue, ^{
        [NSThread sleepForTimeInterval:1];
        NSLog(@"group1");
    });
    
    dispatch_group_async(group, queue, ^{
        [NSThread sleepForTimeInterval:1];
        NSLog(@"group2");
    });
    
    dispatch_group_async(group, queue, ^{
        [NSThread sleepForTimeInterval:1];
        NSLog(@"group3");
    });
    
    dispatch_group_notify(group, dispatch_get_main_queue(), ^{
        NSLog(@"updateUI");
    });

前3個dispatch_group_async執行是異步的,順序不定。

2.3 dispatch_barrier_async的使用

dispatch_barrier_async 是在前面的任務執行結束後它才執行,並且它後面的任務等它執行完成以後纔會執行。示例代碼:

    dispatch_queue_t queue = dispatch_queue_create("gcdtest.rongfzh.yc", DISPATCH_QUEUE_CONCURRENT);
    
    dispatch_async(queue, ^{
        [NSThread sleepForTimeInterval:1];
        NSLog(@"dispatch_async1");
    });
    
    dispatch_async(queue, ^{
        [NSThread sleepForTimeInterval:1];
        NSLog(@"dispatch_async2");
    });
    
    dispatch_async(queue, ^{
        [NSThread sleepForTimeInterval:1];
        NSLog(@"dispatch_async3");
    });
    
    dispatch_barrier_async(queue, ^{
        NSLog(@"dispatch_barrier_async");
        [NSThread sleepForTimeInterval:4];
    });
    
    dispatch_async(queue, ^{
        [NSThread sleepForTimeInterval:1];
        NSLog(@"dispatch_async4");
    });

一樣的,前3個dispatch_async執行是異步的,順序不定。

2.4 dispatch_apply

執行某個代碼片斷N次。

    dispatch_queue_t queue = dispatch_get_global_queue(DISPATCH_QUEUE_PRIORITY_DEFAULT, 0);
    dispatch_apply(5, queue, ^(size_t index) {
        NSLog(@"dispatch_apply: index: %d", index);
    });

 

GCD還有不少其餘用法,能夠參考官方文檔

參考的文檔還有:http://en.wikipedia.org/wiki/Grand_Central_Dispatch

相關文章
相關標籤/搜索