#include<iostream>
#include<thread>
using namespace std;
void func()
{
for (int i = 0; i < 10000; i++)cout << "Print" << endl;
}
int main()
{
thread t(func);
t.detach();
cout << "Exit" << endl;
return 0;
}
在上面的代码中,当主要退出时,"Print"
文本将在哪里消失,因为它没有输出流?是否有用于插入无用的数据的虚拟流?
答案 0 :(得分:5)
当main
退出时,调用exit
会终止所有线程,无论是否分离。这是因为exit
终止了整个过程。
C ++运行时以main
的形式运行exit(main(argc, argv))
,因此从main
返回会导致exit
被调用。
如果您愿意,可以通过拨打pthread_exit
来终止主要主题。在这种情况下,主线程不会从main
返回,也不会调用exit
。应用程序将继续运行,直到某些其他线程调用exit
或所有线程终止(或应用程序崩溃)。这是它在Linux上的工作原理,不确定Windows。
std::cout
对象和其他标准流至少在调用exit
之前可用。这些流使用Schwarz Counter idiom初始化,这确保它们在第一次使用之前初始化,并在最后一个用户消失后销毁。换句话说,如果你有一个带有构造函数和析构函数的全局对象,它会在main
输入之前被初始化并在被调用之后被销毁(当调用exit
时),那个标准流仍然可用在那个全局对象析构函数中。基本上,有一个与每个标准流相关联的引用计数器,每个转换单元(目标文件)在启动时递增此引用计数器,在终止时递减。
ISO / IEC 14882:2011(E)说:
27.4标准iostream对象
27.4.1.2构造对象[标准流]并在第一次构建类
ios_base::Init
的对象之前或期间的某个时间建立关联,并且在任何情况下都在main
开始执行†。程序执行期间不会销毁对象。包含在翻译单元中的结果应该像定义具有静态存储持续时间的ios_base::Init
的实例一样。同样,整个程序的行为应该至少有一个具有静态存储持续时间的ios_base::Init
实例。†静态对象的构造函数和析构函数可以访问这些对象以从
stdin
读取输入或将输出写入stdout
或stderr
。