为什么java中这个递归函数的结果是这样的

why does the result of this recursive function in java is like that

1. static void h2(int n){
2.        if(n<2)
3.            h2(n+1);
4.        System.out.print(n+" ");
5.        if(n<2)
6.            h2(n+1);
7. }

函数h2()是一个递归函数
如果我给 n=0 这个函数的结果是: 2 1 2 0 2 1 2
有人可以向我解释这个功能是如何工作的吗?
我还想知道下一个 ==> 例如在 3 行中,当函数 h2(n+1); 被调用时,代码是否继续到下一行并打印 n 上的值或者它去重新开始这个功能?

我添加了一些印刷品以便我可以看到发生了什么:


1. static void h2(int n){
2.        int i=0;
3.        if(n<2){
4.            System.out.println("i="+(++i)+" first n="+n+" ");
5.            h2(n+1);
6.        }
7.        System.out.println("i="+(++i)+" n="+n);
8.        if(n<2){
9.            System.out.println("\ni="+(++i)+" second n="+n+" ");
10.            h2(n+1);
11.       }
12. }

这是这段代码的输出:

i=1 first n=0 
i=1 first n=1 
i=1 n=2
i=2 n=1

i=3 second n=1 
i=1 n=2
i=2 n=0

i=3 second n=0 
i=1 first n=1 
i=1 n=2
i=2 n=1

i=3 second n=1 
i=1 n=2

这里是一个测试应用程序,向您展示程序执行的轨迹(由于使用String#repeat(int),需要Java11):

public class Main {

  private static int depth;

  public static void main(String[] args) {
    foo(0);
  }

  public static void foo(int n) {
    printDebug("Invoked foo(" + n + ")");

    if (n < 2) {
      printDebug("Recursively call foo(" + n + " + 1)");
      depth++;
      foo(n + 1);
      depth--;
      printDebug("Returned from recursive call of foo(" + n + " + 1)");
    } else {
      printDebug("Skip recursive call");
    }


    // this is the 'System.out.print(n + " "); line'
    printDebug("PRINT VALUE OF n AND A SPACE (n=" + n + ")");

    if (n < 2) {
      printDebug("Recursively call foo(" + n + " + 1)");
      depth++;
      foo(n + 1);
      depth--;
      printDebug("Returned from recursive call of foo(" + n  + " + 1)");
    } else {
      printDebug("Skip recursive call");
    }
  }

  private static void printDebug(String msg) {
    System.out.println("    ".repeat(depth) + msg);
  }
}

递归函数已重命名为 foo 并稍作修改以适应调试语句。当你 运行 以上时,输出将是:

Invoked foo(0)
Recursively call foo(0 + 1)
    Invoked foo(1)
    Recursively call foo(1 + 1)
        Invoked foo(2)
        Skip recursive call
        PRINT VALUE OF n AND A SPACE (n=2)
        Skip recursive call
    Returned from recursive call of foo(1 + 1)
    PRINT VALUE OF n AND A SPACE (n=1)
    Recursively call foo(1 + 1)
        Invoked foo(2)
        Skip recursive call
        PRINT VALUE OF n AND A SPACE (n=2)
        Skip recursive call
    Returned from recursive call of foo(1 + 1)
Returned from recursive call of foo(0 + 1)
PRINT VALUE OF n AND A SPACE (n=0)
Recursively call foo(0 + 1)
    Invoked foo(1)
    Recursively call foo(1 + 1)
        Invoked foo(2)
        Skip recursive call
        PRINT VALUE OF n AND A SPACE (n=2)
        Skip recursive call
    Returned from recursive call of foo(1 + 1)
    PRINT VALUE OF n AND A SPACE (n=1)
    Recursively call foo(1 + 1)
        Invoked foo(2)
        Skip recursive call
        PRINT VALUE OF n AND A SPACE (n=2)
        Skip recursive call
    Returned from recursive call of foo(1 + 1)
Returned from recursive call of foo(0 + 1)

每行的缩进表示递归调用的当前深度(缩进越多表示递归越深)。如果您查看 PRINT VALUE OF n AND A SPACE (n=#) 行的顺序,您将看到原始递归函数的输出将是:

2 1 2 0 2 1 2