GCD指南

GCD指南


基本概念

  • 串行:多個任務(wù)在一條線程順序執(zhí)行。

  • 并發(fā):多個任務(wù)在多條線程同時執(zhí)行。

  • 同步:立即在當(dāng)前線程上執(zhí)行任務(wù),待到任務(wù)結(jié)束后让蕾,再執(zhí)行后面的任務(wù)。

  • 異步:立即在另一條線程上執(zhí)行任務(wù)或听,不等待任務(wù)結(jié)束探孝,立即返回,以執(zhí)行后面的任務(wù)誉裆。

  • 注意再姑,同步和異步都會將任務(wù)添加至目標(biāo)線程的末尾而非在當(dāng)前位置插入找御。


隊(duì)列和執(zhí)行函數(shù)

  • 隊(duì)列:
  • 任務(wù)之間的派發(fā)順序:FIFO元镀。
  • 任務(wù)之間的執(zhí)行順序:串行(前一個執(zhí)行任務(wù)完畢绍填,再執(zhí)行下一個);并行(不等前一個任務(wù)執(zhí)行完畢栖疑,下一個就執(zhí)行)
  • 串行隊(duì)列
  • 局部串行隊(duì)列
    // 創(chuàng)建一個局部串行隊(duì)列
    dispatch_queue_t serialQueue = dispatch_queue_create("SerialQ", DISPATCH_QUEUE_SERIAL);
  • 主隊(duì)列:在主線程上執(zhí)行隊(duì)列任務(wù)的串行隊(duì)列讨永。通常用于將子線程數(shù)據(jù)同步至主線程
    // 獲取主隊(duì)列(全局串行隊(duì)列)
    dispatch_queue_t mainQueue = dispatch_get_main_queue();
  • 并行隊(duì)列
  • 局部并發(fā)隊(duì)列
    // 創(chuàng)建一個局部并發(fā)隊(duì)列
    dispatch_queue_t concurrentQueue = dispatch_queue_create("ConcurrentQ", DISPATCH_QUEUE_CONCURRENT);
  • 全局并發(fā)隊(duì)列
    // 獲取全局并發(fā)隊(duì)列
    dispatch_queue_t globalConcurrentQueue = dispatch_get_global_queue(0, 0); // 參數(shù)傳入兩個0即可
  • 執(zhí)行函數(shù)
  • 執(zhí)行任務(wù)的線程:同步(當(dāng)前線程)遇革;異步(其他線程)卿闹。
  • 線程是否等待任務(wù)結(jié)束:(同步)等待;異步(不等待)萝快。
  • 同步執(zhí)行锻霎,將一個或多個任務(wù)添加至目標(biāo)線程末尾,會阻塞當(dāng)前線程揪漩。
    // 同步執(zhí)行一個隊(duì)列(串行/并行)中的任務(wù)
    dispatch_sync(aQueue, ^{
        // 任務(wù)
    });
  • 異步執(zhí)行旋恼,將一個或多個任務(wù)添加至目標(biāo)線程末尾,不會阻塞當(dāng)前線程奄容。
    // 異步執(zhí)行一個隊(duì)列(串行/并行)中的任務(wù)
    dispatch_async(aQueue, ^{
        // 任務(wù)
    });

隊(duì)列和執(zhí)行函數(shù)組合

組合 同步執(zhí)行 異步執(zhí)行
局部串行隊(duì)列 當(dāng)前線程冰更,順序執(zhí)行 其他線程(一條),順序執(zhí)行
主隊(duì)列 DeadLock 主線程昂勒,順序執(zhí)行
并行隊(duì)列 當(dāng)前線程蜀细,順序執(zhí)行 其他線程(多條),并行執(zhí)行
  • 死鎖/DeadLock:假設(shè)有串行隊(duì)列q戈盈,其中有任務(wù)t1奠衔,t1又包含向隊(duì)列q提交同步執(zhí)行任務(wù)t2的代碼。這時塘娶,q等待t1執(zhí)行完畢涣觉,t1等待t2執(zhí)行完畢,但由于t2需要等待隊(duì)列q中的所有操作執(zhí)行完畢才能執(zhí)行血柳,就造成了DeadLock狀態(tài)官册。
串行隊(duì)列q--(等待)-->任務(wù)t1--(等待)-->任務(wù)t2--(等待)-->隊(duì)列q--->無限循環(huán)
  • 盡管死鎖多發(fā)生在串行隊(duì)列,但對于并行隊(duì)列难捌, 也要避免在任務(wù)中向任務(wù)所在的隊(duì)列提交同步執(zhí)行任務(wù)驰后。

  • 異步執(zhí)行永遠(yuǎn)不會造成DeadLock驻债。

  • 上述表格中捂蕴,只使用異步執(zhí)行 + 各種隊(duì)列的組合端盆。


進(jìn)程間通信

    /**
     在子線程上處理耗時操作,將結(jié)果利用主隊(duì)列同步至主線程击敌。
     */
    dispatch_async(dispatch_get_global_queue(0, 0), ^{
        id result = [self doMyWork]; // 在子線程上應(yīng)該執(zhí)行的任務(wù)
        
        /**
         回到主線程處理結(jié)果
         */
        dispatch_async(dispatch_get_main_queue(), ^{
            [self processResult:result];
        });
        
    });

任務(wù)分組

  • 如果需要等待多個并發(fā)任務(wù)完成后再執(zhí)行某些操作介返,使用任務(wù)分組。
    // 創(chuàng)建一個分組對象
    dispatch_group_t group = dispatch_group_create();
    // 向隊(duì)列提交異步執(zhí)行任務(wù),并將這個任務(wù)納入分組
    dispatch_group_async(group, dispatch_get_global_queue(0, 0), ^{
        NSLog(@"1");
    });
    dispatch_group_async(group, dispatch_get_global_queue(0, 0), ^{
        NSLog(@"3");
    });
    dispatch_group_async(group, dispatch_get_global_queue(0, 0), ^{
        NSLog(@"2");
    });
    dispatch_group_async(group, dispatch_get_global_queue(0, 0), ^{
        NSLog(@"3");
        [NSThread sleepForTimeInterval:3];
    });
    
    /**
     沒有通過分組提交至隊(duì)列的任務(wù)不會被納入分組
     */
    dispatch_async(dispatch_get_global_queue(0, 0), ^{
        [NSThread sleepForTimeInterval:5];
        NSLog(@"獨(dú)立于分組之外的任務(wù)");
    });
    
    // 監(jiān)聽分組內(nèi)所有任務(wù)是否執(zhí)行完畢
    dispatch_group_notify(group, dispatch_get_global_queue(0, 0), ^{
        NSLog(@"所有操作已經(jīng)執(zhí)行完畢");
    });

阻塞隊(duì)列

  • 注意圣蝎,對于全局隊(duì)列來說刃宵,阻塞無效
    dispatch_queue_t queue = dispatch_queue_create(NULL, DISPATCH_QUEUE_SERIAL);
    dispatch_async(queue, ^{
        NSLog(@"1");
    });
    
    dispatch_async(queue, ^{
        NSLog(@"2");
        [NSThread sleepForTimeInterval:3];
    });
    
    /**
     向隊(duì)列提交一個阻塞任務(wù)徘公,當(dāng)隊(duì)列執(zhí)行至阻塞任務(wù)時牲证,不會立即派發(fā)。
     相反关面,隊(duì)列會等到當(dāng)前所有正在執(zhí)行的任務(wù)返回后坦袍,再派發(fā)阻塞任務(wù)。
     阻塞任務(wù)之后的任務(wù)也必須等待其執(zhí)行完畢才能執(zhí)行等太,即前后阻塞捂齐。
     */
    dispatch_barrier_async(queue, ^{
        NSLog(@"3(阻塞任務(wù))");
        [NSThread sleepForTimeInterval:3];
    });
    
    dispatch_async(queue, ^{
        NSLog(@"4");
    });
最后編輯于
?著作權(quán)歸作者所有,轉(zhuǎn)載或內(nèi)容合作請聯(lián)系作者
  • 序言:七十年代末,一起剝皮案震驚了整個濱河市缩抡,隨后出現(xiàn)的幾起案子奠宜,更是在濱河造成了極大的恐慌,老刑警劉巖缝其,帶你破解...
    沈念sama閱讀 206,311評論 6 481
  • 序言:濱河連續(xù)發(fā)生了三起死亡事件挎塌,死亡現(xiàn)場離奇詭異徘六,居然都是意外死亡内边,警方通過查閱死者的電腦和手機(jī),發(fā)現(xiàn)死者居然都...
    沈念sama閱讀 88,339評論 2 382
  • 文/潘曉璐 我一進(jìn)店門待锈,熙熙樓的掌柜王于貴愁眉苦臉地迎上來漠其,“玉大人,你說我怎么就攤上這事竿音『褪海” “怎么了?”我有些...
    開封第一講書人閱讀 152,671評論 0 342
  • 文/不壞的土叔 我叫張陵春瞬,是天一觀的道長柴信。 經(jīng)常有香客問我,道長宽气,這世上最難降的妖魔是什么随常? 我笑而不...
    開封第一講書人閱讀 55,252評論 1 279
  • 正文 為了忘掉前任,我火速辦了婚禮萄涯,結(jié)果婚禮上绪氛,老公的妹妹穿的比我還像新娘。我一直安慰自己涝影,他們只是感情好枣察,可當(dāng)我...
    茶點(diǎn)故事閱讀 64,253評論 5 371
  • 文/花漫 我一把揭開白布。 她就那樣靜靜地躺著,像睡著了一般序目。 火紅的嫁衣襯著肌膚如雪臂痕。 梳的紋絲不亂的頭發(fā)上,一...
    開封第一講書人閱讀 49,031評論 1 285
  • 那天宛琅,我揣著相機(jī)與錄音刻蟹,去河邊找鬼。 笑死嘿辟,一個胖子當(dāng)著我的面吹牛舆瘪,可吹牛的內(nèi)容都是我干的。 我是一名探鬼主播红伦,決...
    沈念sama閱讀 38,340評論 3 399
  • 文/蒼蘭香墨 我猛地睜開眼英古,長吁一口氣:“原來是場噩夢啊……” “哼!你這毒婦竟也來了昙读?” 一聲冷哼從身側(cè)響起召调,我...
    開封第一講書人閱讀 36,973評論 0 259
  • 序言:老撾萬榮一對情侶失蹤,失蹤者是張志新(化名)和其女友劉穎蛮浑,沒想到半個月后唠叛,有當(dāng)?shù)厝嗽跇淞掷锇l(fā)現(xiàn)了一具尸體,經(jīng)...
    沈念sama閱讀 43,466評論 1 300
  • 正文 獨(dú)居荒郊野嶺守林人離奇死亡沮稚,尸身上長有42處帶血的膿包…… 初始之章·張勛 以下內(nèi)容為張勛視角 年9月15日...
    茶點(diǎn)故事閱讀 35,937評論 2 323
  • 正文 我和宋清朗相戀三年艺沼,在試婚紗的時候發(fā)現(xiàn)自己被綠了。 大學(xué)時的朋友給我發(fā)了我未婚夫和他白月光在一起吃飯的照片蕴掏。...
    茶點(diǎn)故事閱讀 38,039評論 1 333
  • 序言:一個原本活蹦亂跳的男人離奇死亡障般,死狀恐怖,靈堂內(nèi)的尸體忽然破棺而出盛杰,到底是詐尸還是另有隱情挽荡,我是刑警寧澤,帶...
    沈念sama閱讀 33,701評論 4 323
  • 正文 年R本政府宣布即供,位于F島的核電站定拟,受9級特大地震影響,放射性物質(zhì)發(fā)生泄漏逗嫡。R本人自食惡果不足惜青自,卻給世界環(huán)境...
    茶點(diǎn)故事閱讀 39,254評論 3 307
  • 文/蒙蒙 一、第九天 我趴在偏房一處隱蔽的房頂上張望祸穷。 院中可真熱鬧性穿,春花似錦、人聲如沸雷滚。這莊子的主人今日做“春日...
    開封第一講書人閱讀 30,259評論 0 19
  • 文/蒼蘭香墨 我抬頭看了看天上的太陽。三九已至呆万,卻和暖如春商源,著一層夾襖步出監(jiān)牢的瞬間,已是汗流浹背谋减。 一陣腳步聲響...
    開封第一講書人閱讀 31,485評論 1 262
  • 我被黑心中介騙來泰國打工牡彻, 沒想到剛下飛機(jī)就差點(diǎn)兒被人妖公主榨干…… 1. 我叫王不留,地道東北人出爹。 一個月前我還...
    沈念sama閱讀 45,497評論 2 354
  • 正文 我出身青樓庄吼,卻偏偏與公主長得像,于是被迫代替她去往敵國和親严就。 傳聞我的和親對象是個殘疾皇子总寻,可洞房花燭夜當(dāng)晚...
    茶點(diǎn)故事閱讀 42,786評論 2 345

推薦閱讀更多精彩內(nèi)容