[英]std::mutex not locking properly for std::cout
我正在學習C ++ 11中的多線程,並且嘗試了這個簡單的測試,但是輸出不是我期望的。
#include <thread>
#include <iostream>
#include <mutex>
int main() {
auto function = [](int x) {
std::mutex m;
m.try_lock();
std::cout << "Hello" << x << std::endl;
m.unlock();
return;
};
std::thread t1(function , 1);
std::thread t2(function, 2);
std::thread t3(function, 3);
std::thread t4(function, 4);
t1.join();
t2.join();
t3.join();
t4.join();
std::cin.get();
return 0;
}
我期望輸出為:
Hello1
Hello2
Hello3
Hello4
(也許不是按此順序,而是每個問候和數字在單獨的行中)
相反,我得到了這樣的東西:
HelloHello21
Hello3
Hello4
要么
HelloHello2
1
Hello3
Hello4
除了互斥鎖顯然不能正確鎖定之外,還有一個令人困惑的問題是,總是Hello2被切成兩半。
編輯:如果有任何區別,請在VS2015中完成(不應該因為它是全部標准?)
您需要使用static
,因為所有線程都必須訪問相同的互斥對象。 另外,如果在您unlock()
之前引發了異常, try_lock()
(或lock()
)也會引起問題。 std::lock_guard<>()
是一種更安全的方法,因此建議使用它,因為它超出函數范圍時將被釋放,無論是通過函數返回還是通過異常。
嘗試對該功能進行以下修訂:
auto function = [](int x) {
static std::mutex m;
std::lock_guard<std::mutex> mylock(m);
std::cout << "Hello" << x << std::endl;
return;
};
有關更多信息,請參見http://en.cppreference.com/w/cpp/thread/lock_guard 。
另外,如果您認為將來可能會更改互斥鎖類型(或只是想花哨),則可以使用推斷的模板類型設置互斥鎖:
std::lock_guard<decltype(m)> mylock(m);
try_lock()
不一定鎖定互斥體。 它可能會鎖定互斥鎖,但可能不會。 它只會嘗試鎖定互斥鎖。 如果已被鎖定,則它不會等到互斥鎖被解鎖后才返回,表明已發生這種情況。
因此,實際上,您的代碼最終無法有效地以任何形式,形狀,物質或形式同步其輸出。
如果您確實想鎖定互斥鎖,請使用lock()
而不是try_lock()
。
編輯:正如其他人指出的那樣,您的代碼有效地為每個線程創建了一個單獨的互斥體,因此您也需要使該互斥體成為static
。
聲明:本站的技術帖子網頁,遵循CC BY-SA 4.0協議,如果您需要轉載,請注明本站網址或者原文地址。任何問題請咨詢:yoyou2525@163.com.