執行緒8--GCD常見用法

有稜角的圓發表於2016-08-01

1.延遲執行

/***********************延遲第一種方法**************************/
    /* 第一種方法,
      呼叫NSObject的方法
     [self performSelector:@selector(run) withObject:nil afterDelay:2.0];
    @1.該方法在那個執行緒呼叫,那麼run就在哪個執行緒執行(當前執行緒),通常是主執行緒。
    @2.如果把該方法放在非同步函式中執行,則方法不會被呼叫
     
    */
//第一種方法:延遲3秒鐘呼叫run函式
/*    
     NSLog(@"列印執行緒----%@",[NSThread currentThread]);
    [self performSelector:@selector(run) withObject:nil afterDelay:2.0];
 */
/**********************延遲第二種方法**********************/

      /****************主佇列***************/
    //可以安排其執行緒(1),主佇列
    dispatch_queue_t queue=dispatch_get_main_queue();
    dispatch_after(dispatch_time(DISPATCH_TIME_NOW, (int64_t)(5.0*NSEC_PER_SEC)), queue, ^{
        NSLog(@"主佇列--延遲執行----%@",[NSThread currentThread]);
    });
    /****************併發佇列***************/
    //可以安排其執行緒(2),併發佇列
    //1.獲取全域性併發佇列
    dispatch_queue_t queue1=dispatch_get_global_queue(DISPATCH_QUEUE_PRIORITY_DEFAULT, 0);
    //2.計算任務執行的時間
    dispatch_time_t when=dispatch_time(DISPATCH_TIME_NOW, (int64_t)(5.0 * NSEC_PER_SEC));
    //3.會在when這個時間點,執行queue中的這個任務
        dispatch_after(when, queue1, ^{
            NSLog(@"併發佇列-延遲執行----%@",[NSThread currentThread]);
        });

2.一次性程式碼

/**************************方法1*************************/
    //缺點:這是一個物件方法,如果又建立一個新的控制器,那麼列印程式碼又會執行,因為每個新建立的控制器都有自己的布林型別,且新建立的預設為NO,因此不能保證改行程式碼在整個程式中只列印一次。
    if (_log==NO) {
        NSLog(@"方法1一次性程式碼");
        _log=YES;
    }
/***************************方法2**************************/
    //使用dispatch_once函式能保證某段程式碼在程式執行過程中只被執行1次
    //整個程式執行過程中,只會執行一次。
    static dispatch_once_t once;
    dispatch_once(&once,^{
        NSLog(@"方法2一次性程式碼");// 只執行1次的程式碼(這裡面預設是執行緒安全的)
    });

3.佇列組

/*************************佇列組**************************/
/*
 提示:使用佇列組可以讓圖片1和圖片2的下載任務同時進行,且當兩個下載任務都完成的時候回到主執行緒進行顯示。
 
 2.使用佇列組解決
  步驟:
     2.1建立一個組
     2.2開啟一個任務下載圖片1
     2.3開啟一個任務下載圖片2
     2.4同時執行下載圖片1\下載圖片2操作
     2.5等group中的所有任務都執行完畢, 再回到主執行緒執行其他操作
*/
    NSLog(@"佇列表開始下載");
    dispatch_group_t group=dispatch_group_create();
    /******************************************/
    //執行1個耗時的非同步操作
    __block UIImage *image1=nil;
    
    dispatch_group_async(group,global_quque, ^{
        NSLog(@"圖片1開始下載");
   image1=[self imageWithURL:@"http://a583.phobos.apple.com/us/r30/Purple4/v4/02/23/ec/0223ec03-ed8e-1c92-26c0-7dec34de6667/mzl.ksnlsaoo.175x175-75.png"];

    NSLog(@"圖片1下載完成--%@",[NSThread currentThread]);
     });
   /*******************************************/
    //執行1個耗時的非同步操作
    __block UIImage *image2=nil;
    dispatch_group_async(group, global_quque, ^{
        NSLog(@"圖片2開始下載");
        image2=[self imageWithURL:@"http://img3.imgtn.bdimg.com/it/u=1790102556,3036052735&fm=21&gp=0.jpg"];
        NSLog(@"圖片2下載完成--%@",[NSThread currentThread]);
        
    });
   /********************************************/
    // 等前面的非同步操作都執行完畢後,回到主執行緒...
    dispatch_group_notify(group, main_queue, ^{
        self.imageView1.image=image1;
        self.imageView2.image=image2;
        UIGraphicsBeginImageContextWithOptions(CGSizeMake(200, 100), NO, 0);
        [image1 drawInRect:CGRectMake(0, 0, 100, 100)];
        [image2 drawInRect:CGRectMake(100, 0, 100, 100)];
        self.imageView3.image=UIGraphicsGetImageFromCurrentImageContext();
        UIGraphicsEndImageContext();
        NSLog(@"圖片合併完成%@",[NSThread currentThread]);
    });
/**************************************************************/
-(UIImage*)imageWithURL:(NSString*)urlstr{
    NSURL *url=[NSURL URLWithString:urlstr];
    NSData *data=[NSData dataWithContentsOfURL:url];
    UIImage *image=[UIImage imageWithData:data];
    return image;
}

 

相關文章