代码之家  ›  专栏  ›  技术社区  ›  Mo.

Java编码标准/最佳实践-中断/继续标签命名约定

  •  19
  • Mo.  · 技术社区  · 16 年前

    有时,带标签的break或continue可以使代码更具可读性。

    OUTERLOOP: for ( ;/*stuff*/; ) {
        //...lots of code
    
        if ( isEnough() ) break OUTERLOOP;
        //...more code
    }
    

    我想知道标签的通用惯例是什么。所有帽子?第一帽?

    10 回复  |  直到 10 年前
        1
  •  16
  •   Craig    16 年前

    如果你必须使用大写字母,这会引起人们对它们的注意,并将它们从错误地解释为“类”名称中挑出。吸引人们的注意还有一个额外的好处,那就是吸引别人的注意,然后重构代码并删除它们。;)

        2
  •  34
  •   Marcus Downing    16 年前

    我不明白“不使用标签”规则的由来。在执行非琐碎的循环逻辑时,要中断或继续的测试并不总是整齐地放在周围块的末尾。

    outer_loop:
    for (...) {
      //  some code
      for (...) {
        //  some code
        if (...)
          continue outer_loop;
        //  more code
      }
      //  more code
    }
    

    是的,像这样的情况经常发生。人们建议我用什么来代替?像这样的布尔条件?

    for (...) {
      //  some code
      boolean continueOuterLoop = false;
      for (...) {
        //  some code
        if (...) {
          continueOuterLoop = true;
          break;
        }
        //  more code
      }
      if (continueOuterLoop)
        continue;
      //  more code
    }
    

    讨厌! 将其重构为一个方法并不能减轻这一点:

    boolean innerLoop (...) {
      for (...) {
        //  some code
        if (...) {
          return true;
        }
        //  more code
      }
      return false;
    }
    
    for (...) {
      //  some code
      if (innerLoop(...))
        continue;
      //  more code
    }
    

    当然,它有点漂亮,但它仍然传递着一个多余的布尔值。如果内部循环修改了局部变量,那么将其重构为一个方法并不总是正确的解决方案。

    为什么你们都反对标签?给我一些坚实的理由,并为上述情况的实际选择。

        3
  •  14
  •   Community CDub    7 年前

    惯例是完全避免贴标签。

    有非常,非常少的有效理由使用一个标签来打破一个循环。突破是可以的,但你可以通过稍微修改你的设计来消除突破的需要。在您给出的示例中,您将提取“大量代码”部分,并将它们放在具有有意义名称的单独方法中。

    for ( ;/*stuff*/; ) 
    {
        lotsOfCode();
    
        if ( !isEnough() )
        {
            moreCode();
        }
    }
    

    编辑: 看到有问题的实际代码( over here )我认为使用标签可能是使代码可读的最佳方式。在大多数情况下,使用标签是错误的方法,在本例中,我认为这是可以的。

        4
  •  7
  •   Anders Sandvig    16 年前

    Sun的Java代码风格似乎更喜欢用与变量相同的方式来命名标签,这意味着CaseCask与小写字母中的第一个字母相同。

        5
  •  2
  •   izb    16 年前

    我见过的最常见的约定就是camel case,就像一个方法名…

    myLabel:
    

    但我也看到了带下划线前缀的标签

    _myLabel:
    

    或者用实验室…

    labSomething:
    

    不过,从其他答案中,你可能会感觉到,你很难找到一种编码标准,除了“不要使用标签”。我想答案是你应该使用任何对你有意义的风格,只要它是一致的。

        6
  •  1
  •   Community CDub    7 年前

    WRT sadie's code example :

    你给

    outerloop:
    for (...) {
      //  some code
      for (...) {
        //  some code
        if (...)
          continue outerloop;
        //  more code
      }
      //  more code
    }
    

    作为一个例子。你说得对。我的最佳猜测是:

    public void lookMumNoLabels() {
      for (...) {
        // some code
        doMoreInnerCodeLogic(...);
      }
    }
    
    private void doMoreInnerCodeLogic(...) {
       for (...) {
          // some code
          if (...) return;
       }
    }
    

    但是有一些例子表明,无论您在做什么逻辑,这种重构都不能正确地进行。

        7
  •  1
  •   Mo.    16 年前

    由于标签很少有用,所以似乎没有明确的约定。Java语言规范有一个带有标签的示例,它们在非ICAP中。

    但在我看来,由于它们是如此罕见,所以最好仔细考虑一下它们是否真的是正确的工具。

    如果它们是正确的工具,那么就把它们全部设置为上限,这样其他开发人员(或者稍后的您自己)就会马上意识到它们是不寻常的。(正如克雷格已经指出的那样)

        8
  •  0
  •   JProgrammer ewernli    16 年前

    Converation/BestPractice仍然不会使用它们,而是重构代码,以便使用Extract-as方法更易于阅读。

        9
  •  0
  •   Michael Neale    16 年前

    它们是Java的Goto,不确定C是否有。我从来没有在实践中使用过它们,我想不出一个避免使用它们不会导致代码更加可读的情况。

    但如果必须的话-我想所有的帽子都可以。大多数人不会使用贴有标签的休息,所以当他们看到代码时,帽子会跳出来,迫使他们意识到发生了什么。

        10
  •  0
  •   RodeoClown    16 年前

    我知道,我不应该用标签。

    但是假设,我有一些代码,可以从标记的中断中获得很多可读性,我应该如何格式化它们。

    莫,你的前提是错的。 问题不应该是“我如何格式化它们?”

    你的问题应该是“我的代码在循环中有大量的逻辑——我如何使它更可读?”

    这个问题的答案是将代码移动到单独的、命名良好的函数中。那你就不需要给休息贴标签了。