gpt4 book ai didi

c++ - 错误处理中如何避免goto

转载 作者:行者123 更新时间:2023-11-30 01:15:01 25 4
gpt4 key购买 nike

我知道带有 goto 的程序是多么可怕和难以阅读,我想像其他人一样不惜一切代价避免使用它们。

但是,我遇到了一个情况,我在编写优雅的程序时很难避免它们。它带有错误处理。我做了很多步骤,如果任何一步出错,程序应该显示一条错误消息,释放一些内存并返回 false。如果一切正常,它应该返回 true

原程序是这样的:

bool init_routine()
{
int errcode; // Error code
errcode = do_someting();
if(errcode != RETURN_SUCCESS)
{
free_some_memory();
std::cerr << "Something went wrong in initialization.";
return false;
}
errcode = do_something_else();
if(errcode != RETURN_SUCCESS)
{
free_some_more_memory(); // Was allocated in the do_something function
free_some_memory();
std::cerr << "Something went wrong in initialization.";
return false;
}
/* The same pattern repeats quite a few times... */
return true; // Everything was ok
}

这很丑陋,因为有些代码是一遍又一遍地复制粘贴,这是不好的做法。我可以使用一个函数,但是该函数无法从被调用方返回 false,因为 C++ 缺少我所说的双重返回指令

另一种方法是使用嵌套的 if :

bool init_routine()
{
int errcode; // Error code
errcode = do_someting();
if(errcode == RETURN_SUCCESS)
{
errcode = do_something_else();
if(errcode == RETURN_SUCCESS)
{
/* The same pattern repeats quite a few times */
if()
{
if()
{
if()
{
return true;
}
}
}
}
free_some_more_memory();
}
free_some_memory();
std::cerr << "Something went wrong in initialization.";
return false;
}

这避免了任何重复并且紧凑。但是,随着嵌套 if 的数量快速增长,缩进会成为阻碍。而且,所有那些if都隐藏了程序简单的控制流程,只是顺序执行指令,错误退出,让读者相信有很多复杂的条件可以遵循。

我认为更自然的另一种方式是:

bool init_routine()
{
int errcode; // Error code
errcode = do_someting();
if(errcode != RETURN_SUCCESS)
{
goto err1;
}
errcode = do_something_else();
if(errcode != RETURN_SUCCESS)
{
goto err2;
}
/* The same pattern repeats quite a few times... */
return true; // Everything was ok

err2:
free_some_more_memory();
err1:
free_some_memory();
std::cerr << "Something went wrong in initialization";
return false;
}

没有重复,唯一的问题是使用了邪恶的goto。我的问题是:

有没有办法不使用 goto,同时不使用重复,不使用异常,并且没有疯狂的缩进?

编辑:为了清楚起见,我不能使用异常,因为我调用的例程来自用 C 编写的外部库,并且我从我的 C++ 代码中调用它们。很抱歉没有早点提到这一点。

最佳答案

如果您绝对必须显式分配,请使用标准集合或智能指针,例如 std::unique_ptr。他们自动进行重新分配。就是这样。

更一般地说,使用带有清理的析构函数的对象(标准集合和智能指针就是这样做的)。这就是众所周知的 RAII,资源获取即初始化。 Google 以了解更多信息,并在教科书的索引中查找。

顺便说一句,将输出混合到通用函数中并不是一个好主意。如果您想在 GUI 程序中使用该代码怎么办?

关于c++ - 错误处理中如何避免goto,我们在Stack Overflow上找到一个类似的问题: https://stackoverflow.com/questions/29230481/

25 4 0
Copyright 2021 - 2024 cfsdn All Rights Reserved 蜀ICP备2022000587号
广告合作:1813099741@qq.com 6ren.com