调试递归函数



我正在遍历下面的代码,我不明白的部分是"Leaving"n值如何变成2,5和10。我理解递归调用的第一部分,直到n==0,return将控件移到else部分并打印(0%2)。节目不应该在那之后停止吗?

void fun2(int n){
    System.out.println("Entering"+n);
    if(n==0)
        return;
   else{
        fun2(n/2);
        System.out.print("Leaving"+n+"---->");       
        System.out.println(n%2);
    }
}

输出:

      Entering5
      Entering2
      Entering1
      Entering0
      Leaving1---->1
      Leaving2---->0
      Leaving5---->1
      Leaving10---->0

首先,我认为您的输出中有一个错误。当我通过调用值为5的fun2()来运行上面的代码时,我得到了除了Leaving10---->0行之外的所有输出。您确定这是在fun2()函数的输出中,还是在您调用fun2()的代码位置的工件中?也许您正在调用值为10的fun2()函数,并省略了输出Entering10的第一行?

此函数通过计算每个二进制数字的值来工作。这是使用%运算符完成的,称为模运算符(也称为余数运算符),位于其他块的最后一行:System.out.println(n%2);

101 = (1*2^2) + (0*2^1) + (1*2^0) = 4 + 0 + 1 = 5

每次迭代都计算2的下一个较低幂,因为它是用n/2调用的。请记住,这里处理的是整数除法,所以没有余数。1/2=0,而不是0.5。但是,整数模函数的作用很好,所以1%2=1(1除以2=0,余数为1)。

下面详细介绍一下该方法的每个递归级别:

  1. n=5,n/2=2,fun2(2),n=2=1
  2. n=2,n/2=1,fun2(1),n%2=0
  3. n=1,n/2=0,fun2(0),n%2=1
  4. n=0,方法返回

当你把单独的控制台输出放在一起时,你会得到101,它是二进制的5。

如果您调用参数值为10的fun2(),您会看到输出1010:

1010 = (1*2^3) + (0*2^2) + (1*2^1) + (0*2^0) = 8 + 0 + 2 + 0 = 10

最新更新