一、簡介
蘋果官方對GCD是這樣說明的:開發者要做的只是定義想執行的任務并追加到適當的Dispatch Queue中。Dispatch Queue是執行處理的等待隊列,我們可以通過dispatch_async等API,在block語法中記述想要執行的處理并將其追加到Dispatch Queue中,Dispatch Queue是按照追加的順序 進行處理,先進先出FIFO。
用代碼表示就是:
dispatch_async(queue,^{
//想執行的任務,這樣執行就是在另一個新開辟的線程中
});
在執行處理時候是有兩種Dispatch Queue,一種是Serial Dispatch Queue串行調度隊列,這個是等待現在執行中的事件處理結束,另一種是Concurrent Dispatch Queue并發調度隊列,這個是不等待現在執行中的事件處理結束。
異步、同步、并行、串行的特點
異步執行:具備開啟新線程的能力,任務創建后可以先繞過,回頭再執行。
同步執行:不具備開啟新線程的能力,任務創建后就要執行完才能繼續往下走。
并行隊列:隊列中的任務同時執行。
串行隊列:隊列中的任務要按順序執行。
組合特點
二、使用
1.異步執行?并行隊列
//1.異步執行+并行隊列
- (void)asyncConcurrent{
//創建一個并行隊列
dispatch_queue_t queue = dispatch_queue_create("queueName", DISPATCH_QUEUE_CONCURRENT);
NSLog(@"---start---%@",[NSThread currentThread]);
//使用異步函數封裝三個任務,三個任務同時執行,不一定是按任務順序打印 可先繞過不執行
dispatch_async(queue, ^{
NSLog(@"任務1---%@", [NSThread currentThread]);
});
dispatch_async(queue, ^{
NSLog(@"任務2---%@", [NSThread currentThread]);
});
dispatch_async(queue, ^{
NSLog(@"任務3---%@", [NSThread currentThread]);
});
NSLog(@"---end---%@",[NSThread currentThread]);
}
打印結果
2.異步執行?串行隊列
- (void)asyncSerial{
//創建一個串行隊列
dispatch_queue_t queue = dispatch_queue_create("queueName", DISPATCH_QUEUE_SERIAL);
NSLog(@"---start---%@",[NSThread currentThread]);
//使用異步函數封裝三個任務 可先繞過不執行 任務必須按添加進隊列的順序挨個執行
dispatch_async(queue, ^{
NSLog(@"任務1---%@", [NSThread currentThread]);
});
dispatch_async(queue, ^{
NSLog(@"任務2---%@", [NSThread currentThread]);
});
dispatch_async(queue, ^{
NSLog(@"任務3---%@", [NSThread currentThread]);
});
NSLog(@"---end---%@",[NSThread currentThread]);
}
打印結果
3.同步執行?并行隊列
- (void)syncConcurrent{
//創建一個并行隊列
dispatch_queue_t queue = dispatch_queue_create("queueName", DISPATCH_QUEUE_CONCURRENT);
NSLog(@"---start---%@",[NSThread currentThread]);
//使用同步函數封裝三個任務
dispatch_sync(queue, ^{
NSLog(@"任務1---%@", [NSThread currentThread]);
});
dispatch_sync(queue, ^{
NSLog(@"任務2---%@", [NSThread currentThread]);
});
dispatch_sync(queue, ^{
NSLog(@"任務3---%@", [NSThread currentThread]);
});
NSLog(@"---end---%@",[NSThread currentThread]);
}
打印結果
4.同步執行+ 串行隊列
(void)syncSerial{
//創建一個串行隊列
dispatch_queue_t queue = dispatch_queue_create("queueName", DISPATCH_QUEUE_SERIAL);
NSLog(@"---start---%@", [NSThread currentThread]);
//使用異步函數封裝三個任務
dispatch_sync(queue, ^{
NSLog(@"任務1---%@", [NSThread currentThread]);
});
dispatch_sync(queue, ^{
NSLog(@"任務2---%@", [NSThread currentThread]);
});
dispatch_sync(queue, ^{
NSLog(@"任務3---%@", [NSThread currentThread]);
});
NSLog(@"---end---%@", [NSThread currentThread]);
}
只要是同步執行就沒法開啟新的線程,所以多個任務之間也一樣只能按順序來執行。
打印結果
5、異步執行+主隊列
- (void)asyncMain{
//獲取主隊列
dispatch_queue_t queue = dispatch_get_main_queue();
NSLog(@"---start---%@", [NSThread currentThread]);
//使用異步函數封裝三個任務 所有任務都可以先跳過,之后再來“按順序”執行
dispatch_async(queue, ^{
NSLog(@"任務1---%@", [NSThread currentThread]);
});
dispatch_async(queue, ^{
NSLog(@"任務2---%@", [NSThread currentThread]);
});
dispatch_async(queue, ^{
NSLog(@"任務3---%@", [NSThread currentThread]);
});
NSLog(@"---end---%@", [NSThread currentThread]);
}
打印結果
6.同步執行+主隊列(死鎖)
- (void)syncMain{
//獲取主隊列
dispatch_queue_t queue = dispatch_get_main_queue();
NSLog(@"---start---%@", [NSThread currentThread]);
//使用同步函數封裝三個任務
dispatch_sync(queue, ^{
NSLog(@"任務1---%@", [NSThread currentThread]);
});
dispatch_sync(queue, ^{
NSLog(@"任務2---%@", [NSThread currentThread]);
});
dispatch_sync(queue, ^{
NSLog(@"任務3---%@", [NSThread currentThread]);
});
NSLog(@"---end---%@", [NSThread currentThread]);
}
原因:
主隊列中的任務必須按順序挨個執行
任務1要等主線程有空的時候(即主隊列中的所有任務執行完)才能執行
主線程要執行完“打印end”的任務后才有空
“任務1”和“打印end”兩個任務互相等待,造成死鎖