【问题标题】:How come Java does not store the value a method calculates when I system.out.println?当我 system.out.println 时,Java 为什么不存储方法计算的值?
【发布时间】:2017-07-31 11:02:44
【问题描述】:

我一直对return 关键字的概念及其行为方式感到困惑。我玩了一会儿,发现了一些我无法解释的行为。

在下面的代码中,我有一个简单的calculateScore() 方法,它有一个公式。当第一个方法调用calculateScore() 时,我要求它打印出结果以跟踪我的号码的情况。我用不同的值做了两次。

我的问题是:为什么highscore的值在第一行代码之后就消失了?

此后它只给我返回值0,然后在我第二次调用时再次重复此过程。我不明白。

如果我将highscore 定义为一个值,那么为什么它的值会消失?如果我要返回finalScore,为什么return 保留它?谢谢。

public class Main {
    public static void main(String[] args) {
        int highScore = calculateScore(true, 800, 5, 100);
        System.out.println("Your Final Score was " + highScore);
        System.out.println(highScore);

        highScore = calculateScore(true, 10000, 8, 200);
        System.out.println("Your Final Score was " + highScore);
        System.out.println(highScore);
    }

    public static int calculateScore(boolean gameOver,
            int score, int levelCompleted, int bonus) {

        if (gameOver) {
            int finalScore = score + (levelCompleted * bonus);
            finalScore +=2000;
            System.out.println(finalScore);
        }

        return 0;
    }
}

这是输出:

Result
 3300
Your Final Score was 0
0
13600
Your Final Score was 0
0

【问题讨论】:

  • 我不太明白这个问题。如果你告诉函数返回 0,那么它总是返回 0。如果你告诉它返回 finalScore 的值,那么这就是它返回的值。如果你告诉它返回 0,你为什么期望它返回别的东西?
  • 你明白return 0; 是做什么的吗?
  • 您正在返回0。这就是您分配给highScore 的值。您只是将finalScore 打印到控制台,而不是将其分配给highScore。你以为你在做什么?

标签: java methods return system.out


【解决方案1】:
   public static int calculateScore(boolean gameOver,
        int score, int levelCompleted, int bonus) {

    int finalScore = 0; 

    if (gameOver) {

        finalScore  =  (score + (levelCompleted * bonus));
        finalScore +=2000;

    }

    return finalScore ;

}

在您的 calculateScore 方法中,您始终返回 0。如果您想获得计算的金额作为分数。你必须从你的方法中返回它。你必须在方法的开头初始化 finalScore 变量。

【讨论】:

    【解决方案2】:

    return 的作用是传回一个值,以便可以使用它。

    你告诉你的函数打印 finalScore 但最后你只传递了数字 0;该变量接收到的值为 0,完全不考虑它计算的结果并在控制台上显示给您。这就是为什么使用System.out.println(highScore); 打印时总是得到 0。

    只需将0 换成finalScore 即可正常工作。

    public class Main {
     public static void main(String[] args) {
        int highScore = calculateScore(true, 800, 5, 100);
        System.out.println("Your Final Score was " + highScore);
        System.out.println(highScore);
    
        highScore = calculateScore(true, 10000, 8, 200);
        System.out.println("Your Final Score was " + highScore);
        System.out.println(highScore);
    }
    
    public static int calculateScore(boolean gameOver,
            int score, int levelCompleted, int bonus) {
    
        if (gameOver) {
            int finalScore = score + (levelCompleted * bonus);
            finalScore +=2000;
            System.out.println(finalScore);
        }
    
        return finalScore;
    }
    }
    

    【讨论】:

    • 那不会编译。
    • 我认为有问题的功能就足够了,但我会编辑它。
    • 仍然无法编译
    【解决方案3】:

    我喜欢将return 视为方法所代表的值。

    你看到这里的calculateScore 可以像变量的值一样使用吗?

    int highScore = calculateScore(true, 800, 5, 100);
    

    你不能用其他方法,比如System.out.println

    int highScore = System.out.println(); // does not compile
    

    这是因为calculateScore 的签名表明它返回一个int,即它可以“表示”一个整数值。但它究竟代表什么价值呢?这一切都取决于return 声明。在这里,您的退货声明说:

    return 0;
    

    这意味着该方法始终表示0 的值。换句话说,

    int highScore = calculateScore(true, 800, 5, 100);
    

    相同
    int highScore = 0;
    

    这就是第二行输出显示为 0 的原因。

    那么方法应该代表什么价值呢? finalScore 变量的值,当然!但显然你只计算gameOver 的高分。您应该在 if 语句的旁边添加一个新的 return 语句:

    if (gameOver) {
        // your original formula and stuff
        return finalScore;
    }
    

    记得保留return 0 语句,因为如果gameOver 为假怎么办?方法代表什么价值?它不能代表什么,因为方法签名说它代表int。所以我觉得这里最合适的做法是return 0

    【讨论】:

      【解决方案4】:

      嗯,你需要改变你认为这工作的方式。

      在方法内定义的变量仅在该方法内保留该值。

      return 的含义不是“保留”或“存储”。意思是“把这个值传给调用这个方法的方法,然后返回到调用它的地方”。

      所以当你有

      void methodA() {
         int a = methodB();
         System.out.println(a);
      }
      
      int methodB() {
         int b = 5;
         return 0;
      }
      

      然后当methodA 调用methodB 时,执行进入methodB 的第一行,它给变量一个数字(但从不使用它),然后return 告诉它值return 为 0,然后它离开methodB 并返回到methodA 中的调用,并将0 交给变量a。正是在这一点(分配),该值被“保留”。你在这里的执行链是:

      • methodB中的变量b中放入5
      • 指定 0 作为从 methodB 返回的值
      • 丢弃变量b,因为我们要离开methodB
      • 返回methodA
      • 将指定值(0)赋给methodA中的变量a
      • 打印变量a的值。

      【讨论】:

        【解决方案5】:

        第一个观察结果:在 calculateScore() 中,您使用名为 finalScore 的变量,而在 main() 方法中,您使用 highScore - 因此即使您的推理是正确的,这两个变量的名称也不会匹配。

        但是即使名称相同,您也会得到相同的结果,因为 java 中的变量不是全局变量而是具有作用域。作为经验法则:当变量在 {} 中包含的块中声明时,它仅在该块中是已知的,并且在执行离开该块时消失。这就是我们有return-statement 的原因:当您的方法需要向调用方法提供结果时,它returns 它然后调用方法可以将其分配给它自己的变量。

        【讨论】:

          最近更新 更多