【问题标题】:Recursion and factorial of a number in PHP [duplicate]PHP中数字的递归和阶乘[重复]
【发布时间】:2014-02-12 08:05:01
【问题描述】:
<?php  
function factorial_of_a($n)  
{  
    if($n ==0)  
    {  
        return 1;  
    }
    else   
    {    
        return $n * factorial_of_a( $n - 1 );  
    }  
}  
print_r( factorial_of_a(5) );
?>  

我的疑问是:

return $n * factorial_of_a( $n - 1 ) ;

在此语句中 - 当 $n = 5$n - 1 = 4 时,它给出的结果为 20。 但是当我运行它时,答案 120 是怎么来的?嗯,120 是正确的答案......我不明白它是如何工作的。我改用for-loop,它工作正常。

【问题讨论】:

  • 又是什么问题?
  • 嗯,问题是“我不明白它是如何工作的” (:
  • 你在问递归是如何工作的吗?
  • 我会回答这个问题,但现在无法回答......这就是我所做的:pastebin.com/JKeNyZAH 递归只是以“循环”方式重新访问命令以有效地返回结果。 (所以重用代码,不必写2次)

标签: php recursion


【解决方案1】:
factorial_of_a(5)

触发以下调用:

5 * factorial_of_a(5 - 1) ->
5 * 4 * factorial_of_a(4 - 1) ->
5 * 4 * 3 * factorial_of_a(3 - 1) ->
5 * 4 * 3 * 2 * factorial_of_a(2 - 1) ->
5 * 4 * 3 * 2 * 1 * factorial_of_a(1 - 1) ->
5 * 4 * 3 * 2 * 1 * 1

所以,答案是 120。

考虑阅读维基百科上的recursive function 文章。

另外,请阅读此相关主题:What is a RECURSIVE Function in PHP?


但是答案 120 怎么来的?

好吧,这个函数会用$n - 1 调用自己,而$n - 1 不等于0。如果是,则函数实际上将结果返回给程序。所以它不会立即返回结果,而参数大于0。它被称为递归的“终止条件”

【讨论】:

    【解决方案2】:

    它将以这种方式工作..

    - factorial_of_a(5); 
    // now read below dry run code from the bottom for proper understanding
    // and then read again from top
    
       - if n = 0 ; false // since [n = 5]
       - else n*factorial_of_a(n-1); [return 5 * 24] 
       // here it will get 24 from the last line since 4*6 = 24 and pass 
       // it to the value of n i.e. **5** here will make it **120**
    
         - if n = 0 ; false [n = 4] 
         - else n*factorial_of_a(n-1); [return 4 * 6] 
         // here it will get 6 from the last line since 3*2 = 6 and pass it 
         // to the value of n i.e. **4** here will make it **24**
    
             - if n = 0 ; false [n = 3] 
             - else n*factorial_of_a(n-1); [return 3 * 2] 
             // here it will get 2 from the last line since 2*1 = 2 and pass it 
             // to the value of n i.e. **3** here will make it **6**
    
                 - if n = 0 ; false [n = 2] 
                 - else n*factorial_of_a(n-1); [return 2 * 1] 
                 // here it will get 1 from the last line since 1*1 = 1 and pass it 
                 // to the value of n i.e. **2** here
    
                     - if n = 0 ; false [n = 1] 
                     - else n*factorial_of_a(n-1); [return 1 * 1] 
                     // here it will get 1 from the last line and pass it 
                     // to the value of n i.e. **1** here
    
                         - if n = 0 ; true // since [n = 0] now it will return 1
                         - return 1;
    

    【讨论】:

    • 解码你的符号需要一些时间,不确定它是否对初学者有帮助......
    • 哎呀,这实际上是我们在数据结构时代用来空转的方式。让我看看如何使它更具可读性。欢迎您的编辑:)
    【解决方案3】:

    你必须记住他是一个递归 当您调用 factorial_of_a(5) 时,它将执行为

    factorial_of_a(5)  
    
    // 5 * 24
    5 * factorial_of_a(4)
    
      // 4 * 6
      4 * factorial_of_a(3)
    
         // 3 * 2
         3 * factorial_of_a(2)
    
             // 2 * 1
             2 * factorial_of_a(1)
    
                 //will return 1 since it is your base condition
                 1 * factorial_of_a(0)
    

    【讨论】:

      【解决方案4】:

      要理解这一点,您需要清楚 递归 的概念。 递归意味着一次又一次地调用一个函数。 每个递归函数都有一个终止情况和一个递归情况。 终止 case 告诉函数何时停止,递归 case 再次调用函数本身。

      在您的代码中,if 条件 $n == 0 标记了终止情况,即如果数字等于 0 并返回 1,则不进行任何计算。 else 部分是递归情况 [ $n*factorial_of_a($n-1) ]

      Now i will explain how it works for $n = 5 :
      
      Since $n is not equal to 0 then else statement is executed which gives 5 *factorial_of_a(4);
      
      Now factorial_of_a(4) is called which gives 4 * factorial_of_a(3);
      
      Now factorial_of_a(3) is called which gives 3 * factorial_of_a(2);
      
      Now factorial_of_a(2) is called which gives 2 * factorial_of_a(1);
      
      Now factorial_of_a(1) is called which gives 1 * factorial_of_a(0);
      
      Now factorial_of_a(0) is called which gives 1
      

      基本上是这样

      factorial_of_a(5) = 5 * 4 * 3 * 2 * 1 = 120
      

      结果就是这样!

      希望对你有所帮助!

      【讨论】:

        猜你喜欢
        • 2017-05-07
        • 1970-01-01
        • 2019-08-06
        • 1970-01-01
        • 1970-01-01
        • 2015-04-16
        • 2016-01-28
        • 1970-01-01
        • 2015-04-19
        相关资源
        最近更新 更多