我正在学习 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
除了互斥量显然没有正确锁定之外,令人困惑的是它总是被切成两半的 Hello1。
编辑:在 VS2015 中完成,如果有任何不同(不应该,因为它都是标准的?)
最佳答案
您需要使用 static
,因为所有线程都必须访问同一个互斥对象。另外,try_lock()
(或 lock()
)如果在到达 unlock()
之前抛出异常,则会导致问题. 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);
关于c++ - std::mutex 没有为 std::cout 正确锁定,我们在Stack Overflow上找到一个类似的问题: https://stackoverflow.com/questions/36466008/