连续成功检查

时间:2010-05-03 06:39:50

标签: language-agnostic exception

你们中的大多数人可能遇到过这种情况,在应用程序可以继续之前必须检查多个事物并且按照一定的顺序,例如在一个非常简单的情况下创建一个监听套接字(socket,bind,listen,accept)等等。)。至少有两种明显的方法(不要逐字逐句):

if (1st_ok)
{
  if (2nd_ok)
  {
  ...

if (!1st_ok)
{
  return;
}

if (!2nd_ok)
{
  return;
}
...

你有没有更聪明的东西,你更喜欢上面的另一个,或者你(如果语言提供)使用例外?

8 个答案:

答案 0 :(得分:4)

我更喜欢第二种技术。第一个问题的主要问题是它增加了代码的嵌套深度,这是一个重要的问题,当你有大量的前提条件/资源分配要检查时,因为函数的业务部分最终被埋没了在条件墙后面(并经常循环)。在第二种情况下,您可以将概念逻辑简化为“我们已经到达并且一切正常”,这样更容易使用。将正常情况保持为尽可能直线更容易理解,尤其是在进行维护编码时。

答案 1 :(得分:2)

这取决于语言 - 例如在C ++中,您可能会使用异常,而在C语言中,您可能会使用以下几种策略之一:

  • if / else阻止
  • goto(处理的“异常”单个goto标签可能
  • 的少数情况之一
  • break循环
  • 中使用do { ... } while (0)

我个人不喜欢函数中的多个return语句 - 我更喜欢在函数末尾有一个公共的清理块,后跟一个return语句。

答案 2 :(得分:1)

这往往是一种风格问题。有些人只喜欢在程序结束时返回,有些人更愿意在需要的地方进行。

我是第二种方法的粉丝,因为它允许简洁明了的代码,并且可以轻松添加文档。

// Checking for llama integration
if (!1st_ok)
{
  return;
}

// Llama found, loading spitting capacity
if (!2nd_ok)
{
  return;
}

// Etc.

答案 3 :(得分:1)

我更喜欢第二个版本。

在正常情况下,检查之间的所有代码都是按顺序执行的,所以我喜欢在同一级别看到它们。通常没有if分支被执行,所以我希望它们尽可能不引人注目。

答案 4 :(得分:1)

我使用第二,因为我觉得它更好,更容易遵循逻辑。他们还说异常不应该用于流量控制,而是用于异常和意外情况。我想看看专业人士对此有何看法。

答案 5 :(得分:1)

怎么样?

if (1st_ok && 2nd_ok) { }

或者是否必须完成某些工作,例如使用套接字的示例

if (1st_ok()  &&  2nd_ok()) { }

答案 6 :(得分:0)

我因为嵌套而避免使用第一个解决方案。

我避免使用第二种解决方案,因为公司编码规则禁止在函数体中使用多个return

当然,编码规则也禁止goto

我的解决方法是使用局部变量:

bool isFailed = false; // or whatever is available for bool/true/false

if (!check1) {
    log_error();
    try_recovery_action();
    isFailed = true;
}

if (!isfailed) {
    if (!check2) {
        log_error();
        try_recovery_action();
        isFailed = true;
    }
}
...

这并不像我想的那么漂亮,但它是我发现最符合我的约束并编写可读代码的最好的。

答案 7 :(得分:0)

对于它的价值,以下是我对这个问题的一些想法和经验。

就个人而言,我倾向于选择你概述的第二个案例。我发现更容易遵循(和调试)代码。也就是说,随着代码的进展,它变得“更正确”。根据我自己的经验,这似乎是首选方法。

我不知道它在现场有多常见,但我也看到条件测试写成......

error = foo1 ();
if ((error == OK) && test1)) {
    error = foo2 ();
}
if ((error == OK) && (test2)) {
    error = foo3 ();
}
...
return (error);

虽然可读(在我的书中总是一个加号)并避免深度嵌套,但总是让我感到震惊的是使用了大量不必要的测试来实现这些目的。

第一种方法,我认为使用频率低于第二种方法。在那些时候,绝大多数时间是因为没有好的方法。对于剩下的几个实例,在成功案例中提取更多表现的基础上是合理的。争论的焦点是处理器会预测前向分支未被采用(对应于 else 子句)。这取决于几个因素,包括架构,编译器,语言,需求......显然,大多数项目(以及项目的大多数方面)都不符合这些要求。

希望这有帮助。