为什么在这个阶乘代码(没有递归)中,步长为-1而不是+1?

时间:2016-10-05 20:54:51

标签: ruby algorithm

为什么在这个计算阶乘的代码中,步长为-1,而不是+1? 它如何计算n = 0,如果在程序中我们只有n <0。 0和n> 0?

def factorial(n)
  if n < 0
    return nil
  end

  result = 1
  while n > 0
    result = result * n

    n -= 1
  end

  return result
end

4 个答案:

答案 0 :(得分:4)

它计算n=0,因为result默认设置为1。当n0时,循环将无法运行(因为n不是> 0),因此默认值为result({{1}将被退回。

每次减去一个,以便它可以向下计数所有数字,所以

  

5! = 5 * 4 * 3 * 2 * 1

如果每次添加一个

  

5! = 5 * 6 * 7 * 8 ......

等等。所以不仅是错误的,而且也是一个无限循环。

答案 1 :(得分:3)

步长是-1,这样你就可以将所有n *(n -1)*(n - 2)* ... * 1的值相乘。由于乘法从n开始并且向下,你想要一步消极。 (或者,你可以从1开始并向上移动到n。在这种情况下,你希望步骤为+1。这不是这个实现的工作方式。)

该程序仍适用于0的输入,因为在while循环之前默认设置为>Description: An unhandled exception occurred during the execution of the current web request. Please review the stack trace for more information about the error and where it originated in the code. >Exception Details: System.TypeLoadException: Method 'ExecuteAsync' in type 'System.Data.Entity.SqlServer.DefaultSqlExecutionStrategy' from assembly 'EntityFramework.SqlServer, Version=6.0.0.0, Culture=neutral, PublicKeyToken=b77a5c561934e089' does not have an implementation. >Source Error: >The source code that generated this unhandled exception can only be shown when compiled in debug mode. To enable this, please follow one of the below steps, then request the URL: >1. Add a "Debug=true" directive at the top of the file that generated the error. Example: <%@ Page Language="C#" Debug="true" %> >or: >2) Add the following section to the configuration file of your application: <configuration> <system.web> <compilation debug="true"/> </system.web> </configuration> 。在这种情况下,循环体被跳过。

答案 2 :(得分:2)

1 * 2 * 3 == 3 * 2 * 1,所以从算术角度来看,无论你是上班还是下班,都无关紧要。但是,递减参数n允许它直接用于计算result,而不是将计算基于另一个单独的变量,该变量会递增直到达到n

那就是说,它仍然不是一种非常红润的做事方式。我可能会选择类似的东西:

def factorial(n)
  n == 0 ? 1 : (1..n).inject(:*)
end

您还询问了您的实施如何将factorial(0)计算为1.如果n == 0永远不会激活while n > 0循环,那么从初始化result = 1开始,您跳到return {1}}陈述。

答案 3 :(得分:1)

步骤为-1且不是+1的原因是因为while循环正在进行while n > 0。所以如果你要做n += 1,你手上就会有无限循环。

如果要使用迭代器设置for循环,则可以启动迭代器并直到iterator <= n。在这种情况下,您可能希望iterator += 1。但在这种情况下,我们只需要将1-n中的所有值相乘,这对顺序不敏感。因此,从n开始并减少代码直到达到零为止,它更简单,代码更少。这就是n -= 1的原因。