异常处理对于新手和有经验的开发人员来说都是一个挑战。人们见过的异常处理反模式有哪些例子?
答案 0 :(得分:3)
糟糕的清理逻辑
从析构函数中抛出清理代码。这个是双坏的,因为a。)从析构函数中抛出通常是坏的b。)因为即使你能抓住它,也没有任何关于它的事情。
File::~File()
{
if (!close(fd_)) {
throw FileIOException("Could not close descriptor.", fd_);
}
}
来自地狱的用户界面
try {
// ... lots of UI logic here ...
} catch (Exception error) {
alert("This program has performed an illegal operation and needs to quit.");
System.exit(-1);
}
无后退重试
bool has_connected = false;
while (!has_connected) {
try {
EstablishConnection();
has_connected = true;
} catch (...) {
// IGNORE
}
}
答案 1 :(得分:3)
这是一个与我以前见过的完全不同的东西。
try {
methodThatThrowsSomeException1();
methodThatThrowsSomeOtherException2();
methodThatThrowsSomeOtherException3();
methodThatThrowsSomeOtherException4();
methodThatThrowsSomeOtherException5();
methodThatThrowsSomeOtherException6();
...
methodThatThrowsYetAnotherException20();
} catch (Throwable e) {
log.error("There was a problem reading the user role");
role = PRIVILEGED;
}
答案 2 :(得分:2)
catch (...)
。
可能是使代码看起来稳定的最糟糕方式......
这同样适用于任何其他语言,您可以捕获您不期望的异常,并且只是静默地吞下它们以隐藏用户的错误。但是(...)
通常用于捕获异常,例如NULL指针取消引用或访问拒绝,这意味着吞下的错误可能会在以后以可能看起来完全与问题的根无关的方式表现出来。
答案 3 :(得分:1)
我最大的烦恼是建立一个异常继承层次结构,其中后代关系对是否应该捕获异常几乎没有影响。关于预定义的异常没什么可做的,但我的首选是避免抛出那些,而是为调用者应该假设系统状态正常的情况定义新的异常,除非例程没有隐含的程度成功返回,而不是系统状态被破坏的那些。例如,如果一个方法应该打开一个文件并返回一个新的文档对象,但解析该文件有一些问题,它不应该杀死整个应用程序。它应该让用户知道文件无法打开,然后继续进行,就像用户没有尝试打开文件一样。文件未打开的原因无关紧要;问题是应用程序状态是否已损坏。不幸的是,没有一个标准例外处理这个问题非常好。
答案 4 :(得分:1)
在共享库中使用异常,这些异常库要用于多种语言/ C ++方言。由于C ++编译器无法保证您不会意外地将异常抛回调用者(与Java不同),因此您只是为崩溃做准备。