class D
{
public:
~D() { throw std::exception(); }
};
int main()
{
try
{
try
{
D d;
}
catch (...)
{
cout << "1";
}
}
catch (std::exception& e)
{
cout << "2";
}
}
Run Code Online (Sandbox Code Playgroud)
我的轻描淡写是,这应该在2中捕获。但是它没有捕获,而是终止了程序。
在C ++ 11中,析构函数是隐式的noexcept,因此,std::terminate如果析构函数抛出未在析构函数本身内捕获的异常,则会自动调用该析构函数。
甚至在此之前,在堆栈展开过程中引发未捕获异常的析构函数也会std::terminate被调用,因此,如果析构函数被使气泡冒泡的其他异常调用,那么您正在执行的操作将无效。
如果这无关紧要,则可以显式声明析构函数为~D() noexcept(false)(如果析构函数不是由引起堆栈展开的其他异常触发的,则异常会冒出析构函数)。
请注意,尽管从技术上讲这是合法的,但在析构函数中引发未捕获的异常通常被认为是一个坏主意,因为这会使您的类在可能引发可处理异常的任何情况下基本上都无法使用。您可以在析构函数中的c ++异常中了解更多信息(这不是严格的重复,但完全涵盖了您的情况)。