C++使用thread類多線程編程


轉自:C++使用thread類多線程編程

C++11中引入了一個用於多線程操作的thread類,下面進行簡單演示如何使用,以及如果進行多線程同步。

thread簡單示例

#include <iostream>  
#include <thread>  
#include <Windows.h>  
  
using namespace std;  
  
void thread01()  
{  
    for (int i = 0; i < 5; i++)  
    {  
        cout << "Thread 01 is working !" << endl;  
        Sleep(100);  
    }  
}  
void thread02()  
{  
    for (int i = 0; i < 5; i++)  
    {  
        cout << "Thread 02 is working !" << endl;  
        Sleep(200);  
    }  
}  
  
int main()  
{  
    thread task01(thread01);  
    thread task02(thread02);  
    task01.join();  
    task02.join();  
  
    for (int i = 0; i < 5; i++)  
    {  
        cout << "Main thread is working !" << endl;  
        Sleep(200);  
    }  
    system("pause");  
}  

輸出:

thread detach不阻塞主線程

兩個子線程並行執行,join函數會阻塞主流程,所以子線程都執行完成之后才繼續執行主線程。可以使用detach將子線程從主流程中分離,獨立運行,不會阻塞主線程:

#include <iostream>  
#include <thread>  
#include <Windows.h>  
  
using namespace std;  
  
void thread01()  
{  
    for (int i = 0; i < 5; i++)  
    {  
        cout << "Thread 01 is working !" << endl;  
        Sleep(100);  
    }  
}  
void thread02()  
{  
    for (int i = 0; i < 5; i++)  
    {  
        cout << "Thread 02 is working !" << endl;  
        Sleep(200);  
    }  
}  
  
int main()  
{  
    thread task01(thread01);  
    thread task02(thread02);  
    task01.detach();  
    task02.detach();  
  
    for (int i = 0; i < 5; i++)  
    {  
        cout << "Main thread is working !" << endl;  
        Sleep(200);  
    }  
    system("pause");  
}  

輸出:

使用detach的主線程和兩個子線程並行執行。

thread帶參數子線程

在綁定的時候也可以同時給帶參數的線程傳入參數:

#include <iostream>  
#include <thread>  
#include <Windows.h>  
  
using namespace std;  
  
//定義帶參數子線程  
void thread01(int num)  
{  
    for (int i = 0; i < num; i++)  
    {  
        cout << "Thread 01 is working !" << endl;  
        Sleep(100);  
    }  
}  
void thread02(int num)  
{  
    for (int i = 0; i < num; i++)  
    {  
        cout << "Thread 02 is working !" << endl;  
        Sleep(200);  
    }  
}  
  
int main()  
{  
    thread task01(thread01, 5);  //帶參數子線程  
    thread task02(thread02, 5);  
    task01.detach();  
    task02.detach();  
  
    for (int i = 0; i < 5; i++)  
    {  
        cout << "Main thread is working !" << endl;  
        Sleep(200);  
    }  
    system("pause");  
}  

輸出:

 

多線程同步mutex

多個線程同時對同一變量進行操作的時候,如果不對變量做一些保護處理,有可能導致處理結果異常:

#include <iostream>  
#include <thread>  
#include <Windows.h>  
  
using namespace std;  
  
int totalNum = 100;  
  
void thread01()  
{  
    while (totalNum > 0)  
    {  
        cout << totalNum << endl;  
        totalNum--;  
        Sleep(100);  
    }  
}  
void thread02()  
{  
    while (totalNum > 0)  
    {  
        cout << totalNum << endl;  
        totalNum--;  
        Sleep(100);  
    }  
}  
  
int main()  
{  
    thread task01(thread01);  
    thread task02(thread02);  
    task01.detach();  
    task02.detach();  
    system("pause");  
}  

部分輸出結果:

有兩個問題,一是有很多變量被重復輸出了,而有的變量沒有被輸出;二是正常情況下每個線程輸出的數據后應該緊跟一個換行符,但這里大部分卻是另一個線程的輸出。

這是由於第一個線程對變量操作的過程中,第二個線程也對同一個變量進行各操作,導致第一個線程處理完后的輸出有可能是線程二操作的結果。針對這種數據競爭的情況,可以使用線程互斥對象mutex保持數據同步。mutex類的使用需要包含頭文件mutex。

#include <iostream>  
#include <thread>  
#include <Windows.h>  
#include <mutex>  
  
using namespace std;  
  
mutex mu;  //線程互斥對象  
  
int totalNum = 100;  
  
void thread01()  
{  
    while (totalNum > 0)  
    {  
        mu.lock(); //同步數據鎖  
        cout << totalNum << endl;  
        totalNum--;  
        Sleep(100);  
        mu.unlock();  //解除鎖定  
    }  
}  
void thread02()  
{  
    while (totalNum > 0)  
    {  
        mu.lock();  
        cout << totalNum << endl;  
        totalNum--;  
        Sleep(100);  
        mu.unlock();  
    }  
}  
  
int main()  
{  
    thread task01(thread01);  
    thread task02(thread02);  
    task01.detach();  
    task02.detach();  
    system("pause");  
}  

多線程中加入mutex互斥對象之后輸出正常:

 


免責聲明!

本站轉載的文章為個人學習借鑒使用,本站對版權不負任何法律責任。如果侵犯了您的隱私權益,請聯系本站郵箱yoyou2525@163.com刪除。



 
粵ICP備18138465號   © 2018-2025 CODEPRJ.COM