Boost线程-超出范围的可能性

Boost thread - Out of scope possibility

本文关键字:范围 可能性 线程 Boost      更新时间:2023-10-16

我对以下代码的准确性很好奇

for(int i=0 ; i<5 ; i++)
{
SomeClass* ptrinst = new SomeClass()
boost::thread t(  boost::bind (&SomeClass::SomeMethod,ptrinst));
......
}

当t超出作用域时,正在运行的线程会发生什么?

由于主线程不调用t.join(),主线程将继续运行它的循环,产生额外的线程,然后继续运行。所以答案是,在当前的编码下,子线程不会与父线程交互(至少不会直接交互)。

还要注意,thread类是一个奇怪的野兽-当你掉出作用域时,唯一发生的事情是,你的主线程不再有一个句柄来调用t.join()。它落在父线程作用域之外的事实对子线程没有任何影响。一旦你通过实例化产生子线程,子线程本质上就与父线程解耦了(好吧,在父线程中可见的全局变量/动态分配的内存对子线程也是可见的,但是如果你想修改/改变那些全局变量,你将需要互斥体)。正如我在文章后面提到的,你需要对线程上下文中的内存可见性和所有权有一个坚实的理解。只看我在这里的评论可能对你没有帮助。

如果你想让主线程等待子线程完成,你需要将这些线程存储在循环外的std::vector<boost::thread> v;中,然后在第二个循环中,在所有这些实例上调用join

你当前的代码看起来有点可疑,因为你通过绑定调用实例方法-这很好,但我通常不会期望实例方法调用delete this;,这意味着它是由父线程来清理(父线程不应该清理,直到子线程完成)。然而,如果没有某种线程同步,它就无法在正确的时间进行清理。因此,几乎可以肯定会出现内存泄漏或某种恶劣的竞争条件(假设您在主线程的...部分中放置了一个delete ptrinst;,试图进行清理)。如果没有某种同步,您可能会在子线程使用指针之前删除它)。

另外,您可能希望使用std::threadstd::bind来代替boost版本。

最后一点:我怀疑您还在尝试使用线程。如果这是真的,那么在尝试修复这段代码之前,最好先阅读并尝试更多更简单的示例。否则,你可能会让自己陷入一个痛苦的世界(调试地狱,包括竞争条件,奇怪的内存同步问题,等等…)。

试着对内存和线程之间发生的事情建立一个更牢固的理解:哪些内存对哪些线程可见,哪些内存可以共享,哪些不能共享。