Main 中的巨大 Try Catch 块
Giant Try Catch Block in Main
我有一个 class 可以在构造函数中抛出异常。我不知道此 class 的代码,因此我无法更改此行为或向此 class 添加其他实例化或初始化方法。我需要在 main 中创建这个 class 的对象。这是否意味着我需要一个主要由一个巨大的 try / catch 块组成的 main() ,如下所示:
main()
{
try
{
A a;
...
}
catch(std::exception& e)
{
std::cout << e.what() << std::endl;
return EXIT_FAILURE;
}
return EXIT_SUCCESS;
}
如果这个main有几千行怎么办?这个 try / catch 块很大。我觉得应该有更好的方法来做到这一点,但我想不出一个。
Does this mean that I need to have a main() that consists mostly of one giant try / catch block
是的。
What if this main is thousands of lines long?
不应该。让它不。将您的功能分解为 函数 !
并且不要忘记 main()
的 return 类型(即 int
)。
What if this main is thousands of lines long?
... I feel like there should be a better way of doing this but I cannot think of one.
这显然是糟糕设计的标志,应该重构为类和函数调用。
理想情况下 main()
:
int main(int argc, char* argv[]) {
try {
Application app(argc,argv);
app.run();
}
catch(std::exception& e) {
std::cout << e.what() << std::endl;
return EXIT_FAILURE;
}
return EXIT_SUCCESS;
}
还是
try {
// Refactored 1000 lines of code
}
catch(std::exception& e) {
std::cout << e.what() << std::endl;
return EXIT_FAILURE;
}
必须附上调用代码。
如果您没有明智的方法来处理异常,那么请不要为 try
块而烦恼。让异常逃逸并取消程序 - 替代方案是在 "world" 不处于正常状态时继续 - 不是一个好主意。
当您没有理智的方法来处理错误时崩溃是合理的。捕获异常是您应该只做的事情如果您有合理的方法来处理它们。默认情况下,让它们传播。
如果您可以明智地处理异常,请在对象的实例化周围添加 try
块,然后在 [=12] 中进行理智的错误处理=]块
有几种不同的方法可以处理这个问题。
在main()
的正文周围放一个function-try-block:
int main() try
{
A a;
// use 'a' as needed ...
return EXIT_SUCCESS;
}
catch (const std::exception& e)
{
std::cout << e.what() << std::endl;
return EXIT_FAILURE;
}
重构代码以将 main()
的大部分移动到另一个函数,然后您可以在 try/except
块中调用该函数:
void run()
{
A a;
// use 'a' as needed ...
}
int main()
{
try
{
run();
return EXIT_SUCCESS;
}
catch (const std::exception& e)
{
std::cout << e.what() << std::endl;
return EXIT_FAILURE;
}
}
就个人而言,我只是在堆上而不是在堆栈上实例化 class。这样,您可以将 try/catch
放在实例化周围:
#include <memory>
int main()
{
std::unique_ptr<A> a; // or std::auto_ptr<A> prior to C++11...
try
{
a.reset(new A);
// or, in C++14 and later:
// a = std::make_unique<A>();
}
catch(const std::exception& e)
{
std::cout << e.what() << std::endl;
return EXIT_FAILURE;
}
// use 'a' as needed ...
// the A object is freed automatically when 'a' goes out of scope...
return EXIT_SUCCESS;
}
我有一个 class 可以在构造函数中抛出异常。我不知道此 class 的代码,因此我无法更改此行为或向此 class 添加其他实例化或初始化方法。我需要在 main 中创建这个 class 的对象。这是否意味着我需要一个主要由一个巨大的 try / catch 块组成的 main() ,如下所示:
main()
{
try
{
A a;
...
}
catch(std::exception& e)
{
std::cout << e.what() << std::endl;
return EXIT_FAILURE;
}
return EXIT_SUCCESS;
}
如果这个main有几千行怎么办?这个 try / catch 块很大。我觉得应该有更好的方法来做到这一点,但我想不出一个。
Does this mean that I need to have a main() that consists mostly of one giant try / catch block
是的。
What if this main is thousands of lines long?
不应该。让它不。将您的功能分解为 函数 !
并且不要忘记 main()
的 return 类型(即 int
)。
What if this main is thousands of lines long?
... I feel like there should be a better way of doing this but I cannot think of one.
这显然是糟糕设计的标志,应该重构为类和函数调用。
理想情况下 main()
:
int main(int argc, char* argv[]) {
try {
Application app(argc,argv);
app.run();
}
catch(std::exception& e) {
std::cout << e.what() << std::endl;
return EXIT_FAILURE;
}
return EXIT_SUCCESS;
}
还是
try {
// Refactored 1000 lines of code
}
catch(std::exception& e) {
std::cout << e.what() << std::endl;
return EXIT_FAILURE;
}
必须附上调用代码。
如果您没有明智的方法来处理异常,那么请不要为 try
块而烦恼。让异常逃逸并取消程序 - 替代方案是在 "world" 不处于正常状态时继续 - 不是一个好主意。
当您没有理智的方法来处理错误时崩溃是合理的。捕获异常是您应该只做的事情如果您有合理的方法来处理它们。默认情况下,让它们传播。
如果您可以明智地处理异常,请在对象的实例化周围添加 try
块,然后在 [=12] 中进行理智的错误处理=]块
有几种不同的方法可以处理这个问题。
在main()
的正文周围放一个function-try-block:
int main() try
{
A a;
// use 'a' as needed ...
return EXIT_SUCCESS;
}
catch (const std::exception& e)
{
std::cout << e.what() << std::endl;
return EXIT_FAILURE;
}
重构代码以将 main()
的大部分移动到另一个函数,然后您可以在 try/except
块中调用该函数:
void run()
{
A a;
// use 'a' as needed ...
}
int main()
{
try
{
run();
return EXIT_SUCCESS;
}
catch (const std::exception& e)
{
std::cout << e.what() << std::endl;
return EXIT_FAILURE;
}
}
就个人而言,我只是在堆上而不是在堆栈上实例化 class。这样,您可以将 try/catch
放在实例化周围:
#include <memory>
int main()
{
std::unique_ptr<A> a; // or std::auto_ptr<A> prior to C++11...
try
{
a.reset(new A);
// or, in C++14 and later:
// a = std::make_unique<A>();
}
catch(const std::exception& e)
{
std::cout << e.what() << std::endl;
return EXIT_FAILURE;
}
// use 'a' as needed ...
// the A object is freed automatically when 'a' goes out of scope...
return EXIT_SUCCESS;
}