server
在这里是一个空类(注释了所有成员以进行测试)。下面的代码(在Win64、MinGW 4.9上编译)将此消息报告给控制台:
应用程序已请求运行时以异常方式终止它。
这里可能有什么问题?
class server {
public:
server() {}
~server(){}
}
...
int main(int argc, char* argv[]) {
std::unique_ptr<server> svr;
std::thread t1([&svr]() {
svr = std::make_unique<server>();
});
std::this_thread::sleep_for(10s);
}
实际上,这段代码产生了相同的结果:
server* svr;
std::thread t1([&svr]() {
svr = new server;
});
delete svr;
这里怎么了?
在这两种情况下看起来都是竞争条件。
在第一个示例中,svr
可能在新线程启动之前就超出了作用域。由于您将对它的引用传递给新线程,如果它在主线程中被破坏,那么新线程将留下一个无效对象。
例如:
void foo()
{
std::unique_ptr<server> svr;
std::thread t1([&svr]() {
// svr might have already been destroyed, UNDEFINED BEHAVIOUR
svr = std::make_unique<server>();
});
// svr goes out of scope and is destructed
}
在第二个示例中,svr
可能在新线程启动之前就被删除了。由于它没有初始化为NULL或nullptr这样的默认值,您可能最终会删除一个悬空指针。
在不考虑指针的情况下,您启动了一个线程,但没有join()
或detach()
线程,这可能会导致您看到的行为。