Day*_*mer 13 c++ exception virtual-destructor
当我们离开catch块范围时,是否会调用异常析构函数?(如果我们不重新抛出它)
假设我有A类,并且它的析构函数不是虚拟的.B继承A.假设某个函数将B类的对象作为异常抛出,并且它被catch块捕获
catch(A& a){
...
}
Run Code Online (Sandbox Code Playgroud)
如果在超出catch范围时应该调用异常析构函数,在这种情况下,只会调用基类A的析构函数?
Cornstalks:实时试验导致调用两个类析构函数.
这与我的逻辑相矛盾.解释某人?
当我们离开catch块范围时,是否会调用异常析构函数?(如果我们不重新抛出它)
是:
[C++11: 15.1/4]:[..]异常对象在异常的最后剩余活动处理程序以除了重新抛出之外的任何方式退出之后被销毁,或者std::exception_ptr引用异常对象的类型(18.8.5)的最后一个对象被销毁,以较晚者为准.[..]
如果在超出catch范围时应该调用异常析构函数,在这种情况下只会调用基类A的de tor?
无:
#include <iostream>
struct A
{
A() { std::cout << "A()"; }
A(const A&) { std::cout << "A(const A&)"; }
A(A&&) { std::cout << "A(A&&)"; }
~A() { std::cout << "~A()"; }
};
struct B : A
{
B() { std::cout << "B()"; }
B(const B&) { std::cout << "B(const B&)"; }
B(B&&) { std::cout << "B(B&&)"; }
~B() { std::cout << "~B()"; }
};
int main()
{
try {
throw B();
}
catch (A&) {
}
}
// Output: A()B()~B()~A()
Run Code Online (Sandbox Code Playgroud)
好的,有人已经回答了你的第一个问题.我将专注于这一个:
如果在超出catch范围时应该调用异常析构函数,在这种情况下只会调用基类A的de tor?
无论如何捕获,实现都将始终正确地销毁异常对象.该实现构造了异常对象,因此它知道如何销毁它.这与delete通过指针调用时不同,因为在这种情况下,new除非存在虚拟析构函数,否则此时对象的完整类型(可能已在其他位置编辑)的信息不完整.
如果不是这样的话,catch (...)根本就不会有用.
| 归档时间: |
|
| 查看次数: |
770 次 |
| 最近记录: |