为什么功能不起作用?

时间:2017-01-20 20:22:31

标签: javascript

所以,我正在浏览“JavaScript Allonge”并且有这个函数来模拟数组的.length函数:

const length = ([first, ...rest]) =>
  first === undefined
    ? 0
    : 1 + length(rest);

现在,如果我将函数重写为:

var lengthy = (first, ...rest) => 
    first === undefined ? 0 : 1 + lengthy(rest)

它给出了Maximum call stack size exceeded,为什么?我打电话给我的版本是这样的:

lengthy(1)

3 个答案:

答案 0 :(得分:3)

您需要在递归调用中使用扩展语法,否则您将传递数组作为第一个参数,然后 rest 参数将是一个空数组。这将无休止地继续下去。

所以:



var lengthy = (first, ...rest) => 
    first === undefined ? 0 : 1 + lengthy(...rest);    
    
console.log(lengthy(1,2,3,8,11));




请注意,在初始调用 rest 是一个数组,其中包含所有剩余的参数。在上面的示例中, rest 将为[2,3,8,11]。这就是其余语法为您所做的。

现在你可以看到你的递归调用看起来如何再次传播该数组:

 lengthy(rest)

...变为

 lengthy([2,3,8,11]) 

所以现在递归调用中的参数是:

 first = [2,3,8,11]
 rest = []

如果您继续进行此分析,您会看到下一个电话是:

 first = []
 rest = []

这将永远持续下去。

现在通过更正lengthy(...rest),实际调用将在示例中:

 lengthy(2,3,8,11) 

......这就是你想要的。现在,firstrest的下一个值将是:

 first = 2
 rest = [3,8,11]

...等

答案 1 :(得分:2)

答案与destructuring有关。

在原文中,你有:

otool

在第二个答案中,您有:

([first, ...rest])

原始数组将一个数组作为参数,并对数组进行解构,以便第一个元素位于(first, ...rest) 中,其余元素位于first中。

第二个不会对数组进行解构,并将您传入的数组放入第一个,使rest成为空数组。这是递归调用的。在对rest的所有递归调用中,lengthy永远不会为空。

答案 2 :(得分:1)

var lengthy = ([first, ...rest]) => first === undefined ? 0 : 1 + lengthy(rest)
// lengthy gets passed ONE argument, an array

这很可能是因为第一个从不评估为0会导致无限循环。

length接受一个参数,即一个数组。

lengthy接受任意数量的参数,并对它们进行计数,但是当你以递归方式调用它时,你只传递它一个。

因此,当第二次调用lengthy时,...restundefined,并在递归调用中传递给lengthy,这意味着first将从此开始undefined并导致您的错误。