在子執行緒呼叫performSelector: withObject: afterDelay 延時方法無效

weixin_33806914發表於2018-04-21

最近在專案中發現performSelector: withObject: afterDelay延時操作有時是無效的,程式沒有繼續執行。經過程式碼的分析發現這種情況一般都是發現在子執行緒中,結合runloop大概分析是以下原因。

  • 程式碼分析
- (void)foo1 {
    dispatch_async(dispatch_get_global_queue(DISPATCH_QUEUE_PRIORITY_DEFAULT, 0), ^{
        [self performSelector:@selector(foo2) withObject:nil afterDelay:2];
    });
}
- (void)foo2 {
    NSLog(@"foo2");
}

在這種情況下程式是沒有任何反應的,foo2並不會在延時之後執行。
我們先看下foo1,在該方法中首先建立一個非同步執行的任務,這時會開闢一個子執行緒,在這個子執行緒中我們去做了一個延時的處理,但是這個延時是基於執行迴圈的,而在子執行緒的runloop預設是不開啟的,需要手動去開啟[[NSRunLoop currentRunLoop] run],所以在這種情況下延時操作是無效的。而在主執行緒runloop是預設開啟的所以一般情況下用performSelector: withObject: afterDelay做延時處理並沒有問題。

相關文章