2015-09-10 102 views
1

我有一个类foo(我不能修改)白衣只有一个构造函数,有一个参数是这样的:Catch构造函数抛出错误?

foo bar("Hello!"); 

由于构造函数可以抛出一个错误,我想要实现的错误处理。我第一次尝试是这样的:

try { 
    foo bar("Hello!"); 
} 
catch { 
    cerr << "Something went horribly wrong..."; 
    return -1; 
} 

不过,现在footry块的范围内,并且不能用于其他地方。如果我理解正确的话,我不能声明对象而不初始化它,所以我可以在try块之外声明bar。那么我该怎么做来捕获构造函数抛出的错误呢?

编辑:澄清,这是在我的main,并在catch我将中止程序。此外,参数是一个将被打开的文件,所以没有已知的安全输入永远不会引发异常。

+4

将所有相关的代码放在try块中。或者在try块中调用的函数中。 – juanchopanza

+0

与相关的代码,你的意思是使用该对象的代码?这意味着我的大部分计划。似乎只是为了捕捉可能仅在初始化期间发生的错误? – Anders

+1

那么,你的程序大部分都可以包含在'main()'函数中,对吧?那么为什么不把它包含在你放入try块的另一个函数中呢? – juanchopanza

回答

3

的问题是相当简单:构造函数失败了,所以从来没有创建bar对象。 C++强制执行此操作,并阻止您在此情况下使用bar

您可能会以另一种方式解决这个问题:

foo makeFoo() 
{ 
    try { 
    return foo("Hello!"); // May throw 
    } 
    catch(...) { 
    return foo("Safe"); // We know that "Safe" will not throw. 
    } 
} 

bar foo{makeFoo()}; 

如果你想,如果抛出异常退出程序,你可以打印一个错误信息,并调用exit(EXIT_FAILURE)渔获内。

+1

感谢您的回答!恐怕没有已知的输入是完全安全的,因为参数是要读取的文件。我认为在C++中没有'null'或类似的东西,我可以返回? – Anders

+1

@Anders:对象不能为空。但指针可以是'nullptr'。这里有'boost :: optional '这可能会或者可能不会持有'foo'。如果你的基本文件丢失,你当然可以打印一条错误消息,并在catch中调用'exit(EXIT_FAILURE)'。 – MSalters

+0

不知道'退出'。这解决了我的问题。谢谢! – Anders

2

你可以使用堆分配:

foo *p = 0; 
try { 
    p = new foo("parm"); 
} catch(const Error& err) { 
    ... 
} 
foo& instance = *p; 
// Here you can use instance normally... 

delete p; // destroy before leaving scope (or use a smart pointer) 
+1

这会让你得到一个空指针解引用。另外,为什么不'std :: unique_ptr'? – MSalters

+0

@MSalters:我假设在catch内部,他会解决这个问题,要么分配一个工作对象,要么只是放弃程序,不要在没有工作对象的情况下超出范围。使用“或使用智能指针”正是我正在考虑的... – 6502

+0

这是在我的'main'中,并在'catch'我只打印一个错误消息和'return'。 – Anders