永发信息网

c++析构函数需要异常处理吗?如需要实现有何要求?

答案:6  悬赏:20  手机版
解决时间 2021-04-06 00:10
  • 提问者网友:無理詩人
  • 2021-04-05 06:40
是老师出的问题其中一道,老师很嚣张,说我们答不出,
哪位c++的前辈可以帮帮忙啊,小弟不胜感激
要举例子啊,麻烦了
最佳答案
  • 五星知识达人网友:人间朝暮
  • 2019-11-19 21:11
delete 〔〕p;

而在释放时发生异常,则这段内存没有被释放掉,造成内存泄漏,因此就要对这个释放做异常处理:

try
{
delete []p;
}
...
在某个地方捕获这个异常,重新进行释放内存处理

事实上...
要杜绝的构造函数里处理异常
全部回答
  • 1楼网友:西岸风
  • 2020-09-26 17:34
按标准,当一个异常处理后如果还有其他悬而未解的异常,那么此时程序将自动调用C++标准库中的terminate()函数...... 好像可以重新抛出异常。
  • 2楼网友:夜余生
  • 2020-02-20 04:04

谁说没有执行! 把析构函数改成下面这句,你就会方法它执行了,你析构函数没有定义操作,怎么会知道执行没有呢?

~stock(){cout << "~stock" << endl;}

  • 3楼网友:猎心人
  • 2019-05-22 15:39
假如目标代码抛出了异常,如果该代码段中某对象的析构函数里也有抛出异常的代码,那么,旧异常的catch块还没有执行的时候,新的异常就被抛出。按标准,当一个异常处理后如果还有其他悬而未解的异常,那么此时程序将自动调用C++标准库中的terminate()函数,该函数默认调用abort()函数非正常结束程序,terminate函数的处理代码也可以自己实现。 #include #include #include using namespace std; void terminator() { cout << "uncaught exception!\n"; // abort(); 标准的terminate默认只调用该函数 exit(0); } void (*old_terminate) = set_terminate(terminator); class foo { public: void f() { throw string("f"); } ~foo() { throw string("~foo"); // 直接或间接(如调用其他函数等)抛出未决异常 }// 没有异常处理代码,即所谓的“逃离了析构函数的异常” }; int main() try { foo a; a.f(); // 一个异常 } // 另一个, i.e. ~foo catch (string& s) { cout << "inside main() catch (...), exception catched: " << s + "\n"; // 不能达到 } 析构函数中如果有异“逃离析构函数的异常”的出现,则多少说明该设计有些失败,原因如上所述,一个程序,动不动就出错退出的话,用户会满意吗?这其中当然还包括由此而引入的内存泄露等问题。 所以从设计原则上来讲,析构函数应杜绝抛出异常(destructors should never emit exceptions),但如果析构函数调用了其他可能会抛出异常的过程,则析构函数自己应该包含处理所有这些子过程可能抛出的异常的代码。 一种不实用的方法,库函数uncaught_exception()在栈回卷(即有未决异常)的时候返回true,可以依此来检测是否已有异常被抛出而且未决,以避免程序非正常退出: #include #include #include using namespace std; void terminator() { cout << "uncaught exception!\n"; // abort(); 标准的terminate默认只调用该函数 exit(0); } void (*old_terminate) = set_terminate(terminator); class foo { enum {something_wrong = 1}; public: void f() { throw string("f"); } ~foo() { // 技术上使用uncaught_exception做异常检测,弃车保帅,知其用则可 if(!uncaught_exception() && something_wrong) throw string("~foo"); // 直接或间接(如调用其他函数等)抛出未决异常 } }; int main() try { foo a; a.f(); // 一个异常 } // 另一个, i.e. ~foo catch (string& s) { cout << "inside main() catch (...), exception catched: " << s + "\n"; } 接下来就是我们的比较“实用”和“正规”的方法:析构函数要包揽所有处理可能在其执行过程中抛出的异常的代码: #include #include #include using namespace std; void terminator() { cout << "uncaught exception!\n"; // abort(); 标准的terminate默认只调用该函数 exit(0); } void (*old_terminate) = set_terminate(terminator); class foo { enum {something_wrong = 1}; public: void f() { throw string("f"); } ~foo() { try { throw string("~foo"); // 直接或间接(如调用其他函数等)抛出未决异常 } catch (string& s) { cout << "inside main() catch (...), exception catched: " << s + "\n"; } } }; int main() try { foo a; a.f(); // 一个异常 } // 另一个, i.e. ~foo catch (string& s) { cout << "inside main() catch (...), exception catched: " << s + "\n"; } 关于更加精辟的解说和一些原则性的指引,请参考: 1、Thinking in C++ 2nd ed Vol.2 Part 1: Building Stable Systems >>> Uncaught exceptions >>> Exception safety 2、Effective C++ 3rd ed >>> Item 8: Prevent exceptions from leaving destructors 一些从书里复制来的话: From Thinking in C++: >>> a destructor that throws an exception or causes one to be thrown is usually a sign of poor design or sloppy coding. >>> It turns out to be practically impossible to design exception-safe code without assuming that destructors don’t throw exceptions. Don’t let destructors throw exceptions. >>> Don’t cause exceptions in destructors Because destructors are called in the process of throwing other exceptions, you’ll never want to throw an exception in a destructor or cause another exception to be thrown by some action you perform in the destructor. If this happens, a new exception can be thrown before the catch-clause for an existing exception is reached, which will cause a call to terminate( ). If you call any functions inside a destructor that can throw exceptions, those calls should be within a try block in the destructor, and the destructor must handle all exceptions itself. None must escape from the destructor. From EC++: >>> Things to Remember ·Destructors should never emit exceptions. If functions called in a destructor may throw, the destructor should catch any exceptions, then swallow them or terminate the program. ·If class clients need to be able to react to exceptions thrown during an operation, the class should provide a regular (i.e., non-destructor) function that performs the operation.
  • 4楼网友:長槍戰八方
  • 2019-12-23 11:45
没必要 你们老师可能是看见某个地方写了什么东西(比如自认为比较好的书上写的),一时自信心膨胀,问这么个鬼问题 一般的软件开发中都不会使用很别扭的东西,风险大,不易修改 鄙视他一下就行了,别放在心上
  • 5楼网友:洎扰庸人
  • 2019-04-06 08:11
理论上... 当你的类中要分配动态内存里就需要在析构函数中进行异常处理 假如在析构函数中要释放一段内存如下: delete 〔〕p; 而在释放时发生异常,则这段内存没有被释放掉,造成内存泄漏,因此就要对这个释放做异常处理: try { delete []p; } ... 在某个地方捕获这个异常,重新进行释放内存处理 事实上... 要杜绝的构造函数里处理异常
我要举报
如以上回答内容为低俗、色情、不良、暴力、侵权、涉及违法等信息,可以点下面链接进行举报!
点此我要举报以上问答信息
大家都在看
推荐资讯