iOS 關於dispatch_semaphore_t 同步執行

weixin_34138377發表於2018-04-17

前言

方法以及作用:當我們在編輯專案時遇到網路請求或者開啟子執行緒執行時,執行緒和請求之外的邏輯需要等待它執行完才可以執行,這時用dispatch_semaphore_t可以滿足需求。

dispatch_semaphore_t 用法

//建立訊號
dispatch_semaphore_t sema = dispatch_semaphore_create(0);
//發射訊號
dispatch_semaphore_signal(sema);
//等待訊號
dispatch_semaphore_wait(sema, 1.0);

使用訊號量 dispatch_semaphore_t 控制請求

- (NSArray  *)p_upData{

        //存放資料
    NSMutableArray * array = [NSMutableArray arrayWithCapacity:0];
        //替代我們平時常用的非同步網路請求
    dispatch_async(dispatch_get_global_queue(0, 0), ^{
        for (int i=0; i<10; i++) {
            [array addObject:[NSNumber numberWithInt:i]];
        }
        NSLog(@"array = %@",array);

    });

    return array;
}

輸出下上面的方法

 NSArray  * dataArray = [self p_upData];
 NSLog(@"dataArray = %@",dataArray);
2018-04-17 10:30:45.868 HTMITest dataArray = (
)
2018-04-17 10:30:45.875 HTMITest array = (
    0,
    1,
    2,
    3,
    4,
    5,
    6,
    7,
    8,
    9
)

想要的結果沒有輸出,但是檢視這個陣列他肯定有值。

  • 現在我們把上述方法修改下,使用訊號量控制,再來看看結果
- (NSArray  *)p_upData{

        //修改下面的程式碼,使用訊號量來進行一個同步資料
        //我們傳入一個引數0 ,表示沒有資源,非0 表示是有資源,這一點需要搞清楚  
//這裡的整形引數如果是非0 就是總資源
    dispatch_semaphore_t sema = dispatch_semaphore_create(0);

        //假如下面這個陣列是用來存放資料的
    NSMutableArray * array = [NSMutableArray arrayWithCapacity:0];
        //下面這個來代替我們平時常用的非同步網路請求
    dispatch_async(dispatch_get_global_queue(0, 0), ^{
        for (int i=0; i<10; i++) {

            [array addObject:[NSNumber numberWithInt:i]];
        }
        NSLog(@"array = %@",array);

        dispatch_semaphore_signal(sema);
    });
    //訊號等待 時,資源數 -1  阻塞當前執行緒 
    dispatch_semaphore_wait(sema, 1.0);
    
    return array;
}
  • 訊號量的理解:
    我們初始化的時候會先設定一個訊號總量,如果訊號總量的整形引數是0 ,那麼就是沒有資源需要等待,我們如果下面執行wait 操作,那麼相當於執行緒擁堵,執行訊號-1 操作
  • 再次看下控制檯的輸出:
2018-04-17 10:36:17.361 HTMITest array = (
    0,
    1,
    2,
    3,
    4,
    5,
    6,
    7,
    8,
    9
)
2018-04-17 10:36:17.364 HTMITest resultArrsy = (
    0,
    1,
    2,
    3,
    4,
    5,
    6,
    7,
    8,
    9
)

相關文章