2013-03-01 98 views
21

通過definition from C++ referencestd :: thread.join()是做什麼的?

阻止當前線程,直到被*this標識的線程完成它的執行。

那麼這是否意味着當使用.join()時,當該線程調用某個函數時不需要mutex.lock()?我是互斥和線程的新手,所以我有點困惑。

注意:我找到了一本書 C++ Concurrency in Action,我在讀這本書。這對於像我這樣的多線程初學者來說是非常好的。

謝謝大家的幫助。

+3

謝謝大衛的編輯使其更加清晰。 馬丁:我試圖谷歌,但我看到4-5樣本有相同的想法,並沒有真正顯示從我的角度來看,聯合正在做什麼..我認爲這裏的人工智能是知識淵博,並會提供代碼的最佳答案樣本。 – Guagua 2013-03-01 03:18:15

回答

17

你仍然需要互斥體和條件。加入一個線程會使一個執行線程等待另一個線程完成運行。您仍然需要互斥體來保護共享資源。它允許這個例子中的main()在退出之前等待所有線程完成。

#include <iostream> 
#include <thread> 
#include <chrono> 
#include <mutex> 

using namespace std; 



int global_counter = 0; 
std::mutex counter_mutex; 

void five_thread_fn(){ 
    for(int i = 0; i<5; i++){ 
     counter_mutex.lock(); 
     global_counter++; 
     counter_mutex.unlock(); 
     std::cout << "Updated from five_thread" << endl; 
     std::this_thread::sleep_for(std::chrono::seconds(5)); 
    } 
    //When this thread finishes we wait for it to join 
} 

void ten_thread_fn(){ 
    for(int i = 0; i<10; i++){ 
     counter_mutex.lock(); 
     global_counter++; 
     counter_mutex.unlock(); 
     std::cout << "Updated from ten_thread" << endl; 
     std::this_thread::sleep_for(std::chrono::seconds(1)); 
    } 
    //When this thread finishes we wait for it to join 
} 
int main(int argc, char *argv[]) { 
    std::cout << "starting thread ten..." << std::endl; 
    std::thread ten_thread(ten_thread_fn); 

    std::cout << "Running ten thread" << endl; 
    std::thread five_thread(five_thread_fn); 


    ten_thread.join(); 
    std::cout << "Ten Thread is done." << std::endl; 
    five_thread.join(); 
    std::cout << "Five Thread is done." << std::endl; 
} 

注意,輸出可能是這樣的:

starting thread ten... 
Running ten thread 
Updated frUopmd atteend_ tfhrroema df 
ive_thread 
Updated from ten_thread 
Updated from ten_thread 
Updated from ten_thread 
Updated from ten_thread 
Updated from five_thread 
Updated from ten_thread 
Updated from ten_thread 
Updated from ten_thread 
Updated from ten_thread 
Updated from ten_thread 
Updated from five_thread 
Ten Thread is done. 
Updated from five_thread 
Updated from five_thread 
Five Thread is done. 

由於性病::法院是它的一個共享資源的訪問和使用也應互斥保護了。

+1

謝謝Joel,那麼這裏的ten_thread.join()會告訴程序ten_thread已經完成,並且可以進入下一步? – Guagua 2013-07-18 18:16:04

+1

運行main()的執行線程將在調用ten_thread.join()時阻塞,直到ten_thread返回。一旦ten_thread執行結束,main的執行就被允許繼續。希望這可以幫助。 – Joel 2013-07-18 20:24:57

6

join()會停止當前線程直到另一個線程完成。互斥鎖會停止當前線程,直到互斥鎖擁有者釋放它或在未鎖定時立即鎖定。所以這些人是完全不同的

+6

雖然我更喜歡「暫停」而不是「停止」。 – Sebastian 2013-03-01 00:15:55

0

的std ::的Thread.join有三個功能,我能想到的副手和其他一些人:

一)鼓勵不斷創建/終端/銷燬線程的,所以錘擊性能並增加了泄漏的probabilty,線程失控,內存失控以及應用程序的一般失控。

b)通過強制執行不需要的等待來填充GUI事件處理程序,導致您的客戶不願意迴應的'沙漏應用程序'。

c)導致應用程序無法關閉,因爲它們正在等待終止不可中斷的不可中斷線程。 d)其他不好的事情。

我知道你是多線程的新手,我希望你能用它做到最好。另外,考慮到我今晚有很多Adnams Broadside,但是:

Join()和它的其他語言中的朋友,如TThread.WaitFor,(Delphi),都是爲了像Windows ME那樣的高效多線程操作系統。

請盡力去發展並理解其他多線程概念 - 池,任務,應用程序生存期線程,通過生產者 - 消費者隊列的線程間通信。實際上,幾乎除Join()之外的任何東西。

+3

您好馬丁,任何推薦閱讀關於多線程在c + +? – Guagua 2013-03-01 03:20:45

1

它會阻塞當前線程,直到線程的執行完成時調用join()。

如果你沒有在線程上指定join()或dettach(),那麼當主/當前線程將完成其執行並且其他創建的線程仍將運行時,它將導致運行時錯誤。