我创建了一个带有一个构造函数和析构函数的类。在main函数中,我创建了一个指针并使用" new"初始化到我的类。关键词。
#include <iostream>
using namespace std;
class RAVI
{
public:
RAVI()
{
cout<<"in constructor"<<endl;
}
~RAVI()
{
cout<<"in Distructor"<<endl;
}
};
int main()
{
RAVI *p;
try{
p= new RAVI();
cout<<"throughng object"<<endl;
throw 6;
}
catch(...)
{
cout<<"Caught exception"<<endl;
}
cout<<"end of try-catch block"<<endl;
return 0;
}
这给出了输出:
in constructor throughng object Caught exception end of try-catch block
通常析构函数应该在抛出异常之前调用。但在下面的案例中为什么不发生?
请澄清我的疑问?
答案 0 :(得分:4)
通常析构函数应该在抛出异常之前调用
<强> WRONG 即可。该对象在堆中分配,并将驻留在内存中,直到程序终止。如果您使用堆栈在try
块中创建对象,那么当该块结束时它将被销毁,但在<{em> throw
之后言。
try{
RAVI p;
cout<<"throughng object"<<endl; throw 6; }
catch(...)
{
cout<<"Caught exception"<<endl;
}
输出:
in constructor
throughng object
in Distructor
Caught exception
end of try-catch block
我猜你假设“通常析构函数应该在抛出异常之前调用”,因为知道如果抛出异常,堆栈将展开并销毁在该范围内创建的所有对象。但对于驻留在堆栈中的对象(包括指针,而不是指向的对象),情况确实如此,而不是在堆中。这是使用智能指针而不是原始指针的动机,因此当堆栈展开时,堆对象也将被销毁。
答案 1 :(得分:1)
离开范围的所有局部变量的析构函数将是
调用。在您的情况下,没有局部变量离开
范围,因此不会调用析构函数。如果RAVI* p;
在
try块,它的析构函数将被调用。但是
指针的析构函数是一个无操作符,所以你无法判断它是否存在
是否被召唤。
当您使用new
创建对象时,您会告诉它
要管理其生命周期的编译器。唯一的一次
当你告诉编译器时,它的析构函数将被调用
这样做,delete
。