我正在Linux上进行多线程C ++提升。
即使我尝试使用锁,以下程序仍然具有竞争条件。
结果为8或9或5。它不应该发生。
#include <iostream>
#include <boost/bind.hpp>
#include <boost/threadpool.hpp>
#include <boost/thread/mutex.hpp>
#include <boost/thread.hpp>
boost::mutex myMutex ;
int g = 0 ;
void f()
{
//myMutex.lock();
{
boost::mutex::scoped_lock lock(myMutex);
++g;
}
//myMutex.unlock();
return ;
}
const int threadnum = 10;
int main()
{
boost::threadpool::fifo_pool tp(threadnum);
for (int i = 0 ; i < threadnum ; ++i)
tp.schedule(boost::bind(f));
std::cout << g << std::endl ;
return 0 ;
}
任何帮助将不胜感激。
谢谢!
答案 0 :(得分:7)
来自http://threadpool.sourceforge.net/tutorial/intro.html:
了解该任务仅适用于此非常重要 执行。安排立即返回,没有任何保证 关于何时执行任务以及处理将持续多长时间 取。
您安排了10个任务,然后立即打印结果,直到您到达该行
时执行的数量为止std :: cout&lt;&lt; g&lt;&lt; std :: endl;
因此,虽然您的互斥锁确保线程一次增加一个g,但您不会在打印结果之前等待它们完成。 修改代码的一种方法是等待池中的所有任务完成:
boost::threadpool::fifo_pool tp(threadnum);
for (int i = 0 ; i < threadnum ; ++i)
tp.schedule(boost::bind(f));
tp.wait(); //WAIT FOR TASKS TO EXECUTE
std::cout << g << std::endl ;
return 0 ;
答案 1 :(得分:5)
我不确定我是否正确阅读,但看起来你正在安排一些会增加g的东西,然后在g的内容上调用cout。你的互斥体会阻止预定的触发器相互踩踏,但是没有任何东西迫使cout在最后等待它们全部完成。你需要某种读/写互斥量。
答案 2 :(得分:0)
似乎主要线程在孩子们之前完成 - 这就是为什么你得到看似随机的g值。有许多方法可以使主线程等到子项完成,即