You need to enable JavaScript to run this app.
优惠活动
大模型
产品
解决方案
定价
更多

JavaScript递归中的递减操作:两个阶乘函数为何输出不同?

两段阶乘递归代码的差异及输出异常原因

先看两段代码的具体实现:

// 第一段代码(正确计算阶乘)
const factorial = (n) => {
  if (n === 0) return 1;
  return factorial(n - 1) * n;
};
console.log(factorial(5)); //Output: 120

// 第二段代码(输出异常)
const factorial = (n) => {
  if (n === 0) return 1;
  return factorial(--n) * n;
};
console.log(factorial(5)); //Output: 0

核心区别

两段代码的核心差异在于递归调用时对参数n的处理方式:

  • 第一段用n - 1传递参数:这是单纯的数值计算,只会把n减1后的结果传给下一次递归,当前函数作用域内的n值不会发生变化。
  • 第二段用--n传递参数:--是前置自减运算符,会先把当前作用域内的n值直接减1,再将减后的值传给递归调用,当前n的值被永久修改。

第二段代码输出0的原因

我们一步步拆解factorial(5)的执行流程就能明白:

  1. 调用factorial(5):n≠0,执行factorial(--5) * 5——先把n改成4,再调用factorial(4),后续乘法用的是已经变成4的n。
  2. 调用factorial(4):n≠0,执行factorial(--4) * 4——n改成3,调用factorial(3),乘法用3。
  3. 调用factorial(3):n≠0,执行factorial(--3) * 3——n改成2,调用factorial(2),乘法用2。
  4. 调用factorial(2):n≠0,执行factorial(--2) * 2——n改成1,调用factorial(1),乘法用1。
  5. 调用factorial(1):n≠0,执行factorial(--1) * 1——关键步骤:先把n改成0,调用factorial(0)返回1,然后乘法用的是已经变成0的n,所以这一步的结果是1 * 0 = 0。
  6. 递归回溯:后续所有上层调用都会用这个0去乘当前的n值,最终结果自然是0。

简单来说,就是--n修改了当前作用域的n值,导致最底层递归返回后,乘的是已经被改成0的n,直接让整个计算链的结果变成0。

内容的提问来源于stack exchange,提问作者Evgeniy

相关产品推荐
方舟 Agent Plan

超全模态模型 × Harness 升级,最新支持 Deepseek-V4.1-Flash、GLM-5.3 系列、Doubao-Seedream-5.0-pro、Kimi-K3 (部分), 限时 9.9 元起

最近更新时间:2026.07.21 12:37:25