【问题标题】:std::thread C++ 11 fails to explain me whystd::thread C++ 11 无法解释为什么
【发布时间】:2014-07-06 13:01:48
【问题描述】:

我在 Ubuntu 13.04 桌面上运行这个非常简单的程序,但是如果我注释掉 sleep_for 行,它会在从 main 打印 cout 后挂起。谁能解释为什么?据我了解, main 是一个线程, t 是另一个线程,在这种情况下,互斥锁管理共享 cout 对象的同步。

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

using namespace std;
std::mutex mu;

void show()
{
 std::lock_guard<mutex> locker(mu);
 cout<<"this is from inside the thread"<<endl;
}

int main()
{
 std::thread t(show);
 std::this_thread::sleep_for(std::chrono::milliseconds(1000));
 std::lock_guard<mutex> locker(mu);
 cout<<"This is from inside the main"<<endl;
 t.join();
 return 0;
}

【问题讨论】:

  • 这是一个常见的代码质量要求的原因,即任何析构函数具有副作用的对象都应在作用域的开头创建,除非有充分的理由不这样做。

标签: multithreading c++11


【解决方案1】:

如果你改成main函数如下,代码将按预期工作:

int main()
{
    std::thread t(show);
    {
        std::lock_guard<mutex> locker(mu);
        cout << "This is from inside the main" << endl;
    } // automatically release lock
    t.join();
}

在您的代码中,有一个不幸的竞态条件。如果线程t 首先获得锁,那么一切正常。但是如果主线程首先获得锁,它会持有锁直到main 函数结束。这意味着,线程t 没有机会获得锁,无法完成,主线程将阻塞t.join()

【讨论】:

    【解决方案2】:

    这只是一个典型的死锁:主线程获得锁,然后在加入另一个线程时阻塞,但只有当 设法获得锁时,另一个线程才能加入。

    【讨论】:

      猜你喜欢
      • 1970-01-01
      • 1970-01-01
      • 1970-01-01
      • 2012-10-17
      • 2014-10-02
      • 1970-01-01
      • 1970-01-01
      • 1970-01-01
      • 2013-05-22
      相关资源
      最近更新 更多