繁体   English   中英

为什么在抛出异常时析构函数调用两次?

[英]why destructor called twice when exception is thrown?

我很困惑,为什么在抛出异常时调用两次调用析构函数,以及在哪一点被调用?

#include <iostream> 
using namespace std;
class base
{
 public:
     base(){cout<<"constructor called"<<endl;}
     ~base(){cout<<"destructor called"<<endl;}
};
void fun()
{
     throw base(); //<=- Create temp obj of base, and throw exception

}
int main()
{
    try
    {
        fun();
    }
    catch(...)
    {
        cout<<"handle all exception"<<endl;
    }

}

以下是输出

constructor called
destrctor called
handle all exception
destuctor is called

但是当我添加复制构造函数时,它从不调用,而析构函数仅调用一次,所以发生了什么?

#include <iostream> 
using namespace std;
class base
{
 public:
     base(){cout<<"constructor called"<<endl;}
     ~base(){cout<<"destructor called"<<endl;}
     base (base &obj){cout<<"copy constructor called"<<endl;}
};
void fun()
{
     throw base(); //<=- Create temp obj of base, and throw exception
}
int main()
{
    try
    {
        fun();
    }
    catch(...)
    {
        cout<<"handle all exception"<<endl;
    }

}

输出:

constructor called
handle all exception
destrctor called

因为异常对象是在catch中复制的。 使用catch (base&v)来获取引用而不是值。

编译器可以根据需要多次复制您的异常对象。 析构函数被调用两次,因为有一个副本。

因为catch块获取原始对象的副本。

为了避免复制,将try-catch编写为:

try
{
    fun();
}
catch(const base &e)
{
    cout<<"handle all exception"<<endl;
}

我也想对设计发表评论:用户定义的异常类应从std::exception或其派生类之一派生。

暂无
暂无

声明:本站的技术帖子网页,遵循CC BY-SA 4.0协议,如果您需要转载,请注明本站网址或者原文地址。任何问题请咨询:yoyou2525@163.com.

 
粤ICP备18138465号  © 2020-2024 STACKOOM.COM