我想知道下面的代码是否被认为是线程安全的。我认为它应该是,但我不太熟悉引擎盖下发生的事情。
基本上,我在类 Foo 中有这个函数,它将在主线程上调用,并将 vector 作为参数,即,
void Foo::func( vector<int> v)
在Foo中,我也有一个私有(private)成员,
vector< vector<int> > vecOfVec;
在 func
中,我将简单地将任何新的 v
推回 vecOfVec
并检查 v
'大小。如果 v
小于预期大小,我想启动另一个线程,用一些已知的预定值填充 v
,如下所示
void Foo::func( vector<int> v)
{
int size = v.size();
int index = vecOfVec.size();
vecOfVec.push_back(v);
if (size < 1000)
{
boost::thread t( boost::bind( &Foo::PushBackZeros, this, vecOfVec, index) );
}
}
Foo::PushBackZeros
,顾名思义,只需用零填充“vecOfVec[index]”处的 vector ,直到其大小增长到 1000;
现在,我没有在 vecOfVec
的任何元素上看到任何并发读取或写入操作。显然,有可能对整个对象进行并发操作,但永远不会对 vecOfVec
的特定元素进行并发操作。
有人可以解释一下上面的内容是否被认为是线程安全的吗? STL映射也会有同样的程度吗?如果不是,请解释。干杯!
最佳答案
我认为,这不是线程安全的。如果一个线程将一个新元素推送到 vector 上,导致 vector 的内部内存区域需要增长,会发生什么情况?推送线程可能会将内存换成更大的缓冲区,这会导致与此操作并行读取的线程突然从无效(已处理)内存中读取。或者线程在某些槽中看到随机值,只是因为它们并发读取代码,将 vector 的内容从旧内存位置复制到新内存位置。
关于C++ STL map/vector of vectors 和线程安全,我们在Stack Overflow上找到一个类似的问题: https://stackoverflow.com/questions/4725367/