代码之家  ›  专栏  ›  技术社区  ›  HbnKing

为什么不能将条件添加到外部循环

  •  2
  • HbnKing  · 技术社区  · 8 年前

    这是我的演示,很简单,但我不能添加到外循环 i<10 如果我试着补充,它提醒我:

    此方法必须返回字符串类型的结果

    public String testFor() {
        for(int i = 0; ; i++) {
            for(int j = 0; j < 10; j++) {
                 return "success";
            }
        }
    }
    

    为什么会这样?

    5 回复  |  直到 8 年前
        1
  •  2
  •   Andy Turner    8 年前

    jls的相关部分是 Sec 8.4.7 Method body ;相关部分是:

    如果一个方法被声明为有一个返回类型(8.4.5),那么如果该方法的主体能够正常完成(14.1),就会发生编译时错误。

    ( "complete normally" 有点混乱的术语;它基本上意味着不执行 return , throw 或 System.exit 声明)

    和 Sec 14.21, Unreachable statements . 相关部分是:

    一个非空的非交换块可以正常完成,除非它的最后一条语句可以正常完成。

    …

    basic for语句通常可以完成,但前提是至少满足以下条件之一:

    • for语句是可访问的,有一个条件表达式,条件表达式不是值为true的常量表达式(§15.28)。
    • 有一个可到达的break语句退出for语句。

    如果for语句是可访问的,并且条件表达式不是值为false的常量表达式,则包含的语句是可访问的。

    内部循环实际上与行为无关:您将看到完全相同的行为:

    public String testFor() {
      // Compiler error if you uncomment the condition.
      for(int i = 0; /* i<10 */; i++) { 
      }
    }
    

    如果没有条件,则两个项目符号条件都不是真的,因此循环无法正常完成;因此,它无法到达循环之后。因此,不 返回 (或) 扔 系统出口 )语句是必需的。

    如果你加上条件 i<10 ,这不是编译时常量,因此循环可以正常完成。因此,您需要添加 返回 (或) 扔 或 系统出口 )循环后的语句。

        2
  •  3
  •   Robby Cornelissen    8 年前

    内环和 return 声明在这里不重要。

    下面的代码片段将编译,而不存在 返回 声明:

    public String testFor() {
        for (int i = 0; ;i++) {
        }
    }
    

    该行为是在Java语言规范中指定的( JLS §8.4.7 ):

    如果方法声明为具有返回类型 ( §8.4.5 ) 如果方法体可以 正常完成 ( §14.1 )

    在这种情况下,由于无限循环,方法主体无法正常完成,因此返回语句(或其他异常终止,例如 throw SomeException() )不是必需的。

        3
  •  1
  •   Ahmed Ashour chim    8 年前

    好吧,有:

    for(int i = 0; ; i++) {
    }
    

    这实际上与

    int i = 0;
    while (true) {
        ...
        i++
    }
    

    所以编译器知道,这是一个无限循环。

    然而,

    for(int i = 0; i < 10; i++) {
    }
    // what to return here?
    

    此循环完成时,编译器需要返回一个字符串。 它不会真正进入第二个 for ,以知道它第一次进入时会返回。 它并没有评估第二个循环,正如Jaroslaw Pawlak暗示的那样

        4
  •  0
  •   Ahmed Ashour chim    8 年前

    因为如果向外部循环添加条件,则应至少向调用方返回一个字符串类型的返回保证,因此代码应如下所示:

    public String testFor() {
         for (int i = 0; i < 10; i++) {
             for (int j = 0; j < 10; j++) {
                  return "success";
              }
         }
         return null;
    }
    
        5
  •  -1
  •   skonline90    8 年前

    编辑:当我回答时,代码看起来不同了…

    public String testFor()
    {
        for (int i = 0;; i++)
        {
            for (int j = 0; j < 10; j++)
            {
                return "success";
            }
        }
    }
    

    这段代码也能正常工作。”j++“是死代码,因为在返回“success”之前,我们只进入一次内部循环。