究竟何时是析构函数或终止于调用的线程
Posted
技术标签:
【中文标题】究竟何时是析构函数或终止于调用的线程【英文标题】:When exactly is a destructor or terminate on a thread called 【发布时间】:2019-10-06 06:51:51 【问题描述】:我正在使用 C++11 std::thread。我的困惑基于以下几点:
如果一个线程上的join()
和detach()
都没有被调用,则调用该线程上的terminate()
。
这意味着当一个线程返回时:
a.它检查是否调用了join()
或detach()
,如果没有,则调用terminate()
(产生一个coredump),
b.如果join()
被调用,线程的析构函数将被main(或调用线程)调用
c.如果在线程执行时调用了detach()
,线程不会返回主线程进行清理,而是由该线程自己负责调用它自己的析构函数
问题:如果上述几点是正确的,那么我不明白 在哪个确切点是决定终止线程还是不是基于是否调用了join()
或detach()
?
void function_1()
return;
int main()
std::thread t1(function_1);
std::cout<<"\nFirst Sleep for 5 seconds:\n";
sleep(5);
cout<<"\n2nd Sleep for 5 seconds:\n";
sleep(5);
if(t1.joinable())
cout<<"\nGonna join()\n";
t1.detach();
cout<<"Exiting from main ...\n";
由于线程将在第 5 秒之前完成执行,我假设线程应该被终止,因为到目前为止还没有 join()/detach()
。但是没有调用terminate()
。而是成功分离了一个线程。
但是,如果我不分离,则在 "Exiting from main...."
之后的 2 次睡眠后调用终止,就在 return 0;
之前
这是否意味着线程没有被清理(它的析构函数没有被调用),直到主线程(或被调用的线程)返回?
这就是为什么要detach()
以便线程的清理不必等到主线程(或调用者线程)返回的原因吗?
【问题讨论】:
【参考方案1】:您似乎混淆了两件事:std::thread
对象,以及该对象管理的执行线程。
对std::terminate
的调用由std::thread
对象的析构函数触发如果它是可连接的。这与std::thread
对象管理的执行线程是否执行完毕没有直接关系。
在您的代码中,t1
的析构函数将触发std::terminate
。 t1
是一个普通的C++对象,这里是main
的局部变量。当它的作用域结束时它会被破坏——这里是 main 的结尾。因此,您必须在主返回之前使t1
不可加入,方法是在t1
上调用join
或detach
。 function_1
是否已完成在其执行线程上的运行无关紧要。
【讨论】:
以上是关于究竟何时是析构函数或终止于调用的线程的主要内容,如果未能解决你的问题,请参考以下文章