15

MISRA 14.5 说不能使用 continue 语句。谁能解释原因?谢谢你。

4

4 回答 4

24

这是因为关于无条件分支和意大利面条代码的古老争论goto已经持续了 40 年左右。goto, continue,break和多个return语句都被认为或多或少同样糟糕。

世界编程社区的共识大致是这样的:我们认识到,如果您知道自己在做什么,那么您可以使用该语言的这些功能而无需编写意大利面条式代码。但是我们仍然不鼓励他们,因为不知道自己在做什么的人很有可能会使用可用的功能,然后创建意大利面条。我们也不鼓励使用它们,因为它们是多余的功能:您显然可以在不使用它们的情况下编写程序。

由于 MISRA-C 是针对关键系统的,MISRA-C:2004 有办法尽可能多地禁止这些无条件分支功能。因此,,gotocontinue多次退货被禁止。break只有在同一个循环中有一个中断时才允许。

然而,在目前正在评估的“MISRA-C:2011”草案中,委员会已经考虑再次允许所有这些功能,但限制 goto 只能向下跳转,不能向上跳转。委员会的理由是现在有足够聪明的工具(即静态分析器)来发现不良程序流,因此可以允许关键字。

goto 辩论仍在进行中...

于 2012-06-12T11:18:24.693 回答
5

众所周知,用 C 语言编程使得跟踪多个执行分支变得非常困难。如果您在某处分配资源,则必须在其他地方(非本地)释放它们。如果您的代码分支,您通常需要为每个分支或退出范围的方式具有单独的释放逻辑。

continue语句添加了另一种退出for循环范围的方法,从而使这样的循环更难推理和理解控制流经它的所有可能方式,这反过来又使确定代码的行为变得更加困难在所有情况下都正确。

这只是我的猜测,但我认为试图限制来自这种额外分支行为的复杂性是你提到的规则的驱动原因。

于 2012-06-11T07:13:48.860 回答
4

我刚碰到它。我们有物品,其中

  • 应该检查几件事,
  • 检查需要一些准备,
  • 我们应该先用便宜的支票,然后用昂贵的支票,
  • 一些检查取决于其他检查,
  • 无论哪个项目在任何检查中失败,都应该记录下来,
  • 如果该项目通过了所有检查,则应将其传递给进一步处理。

观看此视频,无需继续

foreach (items) {

   prepare check1
   if (check1) {

      prepare check2
      if (check2) {

        prepare check3
        if (check3) {
          log("all checks passed")
          process_good_item(item)
        } else {
          log("check3 failed")
        }

      } else {
        log("check2 failed")
      }

   } else {
      log("check 1 failed")
   }    
}

...并与此进行比较,继续

foreach (items) {

   prepare check1
   if (!check1) {
      log("check 1 failed")
      continue
   }

   prepare check2
   if (!check2) {
      log("check 2 failed")
      continue
   }

   prepare check3
   if (!check3) {
      log("check 3 failed")
      continue
   }

   log("all checks passed")
   process_good_item(item)
}

假设“prepare”-s 是多行,所以你不能一次看到整个代码。

自己决定,即

  • 不太复杂,有一个更简单的执行图
  • 具有较低的圈复杂度值
  • 更具可读性,更线性,没有“眼跳”
  • 更好的可扩展性(例如尝试添加 check4、check5、check12)

恕我直言,米斯拉在这个话题上是错误的。

于 2020-04-20T16:26:48.240 回答
1

与所有 MISRA 规则一样,如果您能证明其合理性,您可以偏离规则(MISRA-C:2004 的第 4.3.2 节)

MISRA(和其他类似指南)背后的要点是捕获通常会导致问题的事物……是的,continue可以正确使用,但有证据表明这是导致问题的常见原因。

因此,MISRA 创建了一条规则来防止其(ab)使用,并且审查社区批准了该规则。用户社区的意见普遍支持该规则。

但是我再说一遍,如果你真的想使用它,并且你可以根据你的公司层次结构证明它是合理的,那就偏离。

于 2012-09-27T09:49:59.350 回答