繁体   English   中英

您可以在递归过程中使用.shift()更改数组吗?

[英]Javascript - Can you use .shift() to alter an array during recursion?

我编写了一个递归函数,以确定数组是否包含要添加的必需元素并形成目标数字。 但是这样做时,在尝试使用.shift()删除数组中的第一个元素时遇到错误(第8行):

function findCombo(collection, target){
  if(target === 0){
   return true; 
  } else if(collection.length === 0){
   return false; 
  } else{
    var next = collection[0];
    //collection.shift(); **does not work**
    collection = collection.slice(1); //**works**
    return findCombo(collection, target - next) 
           || findCombo(collection, target);
  }
}

当我意识到collection.shift()是问题时,我尝试将数组更改为collection.slice(1),该程序现在可以运行了。 即使现在,我仍然不明白为什么.shift()无法应用所需的结果。 有谁知道为什么吗?

由于shift()会修改原始集合对象,因此findCombo(collection, target)findCombo(collection, target - next)之后执行findCombo(collection, target)方法时findCombo(collection, target - next)集合对象将为空。

 function findCombo(collection, target) { snippet.log(target + ':' + collection) if (target === 0) { return true; } else if (collection.length === 0) { return false; } else { var next = collection[0]; collection.shift(); //**does not work** //collection = collection.slice(1); //**works** return findCombo(collection, target - next) || findCombo(collection, target); } } snippet.log(findCombo([1, 2, 3, 4, 5], 20)); 
 <!-- Provides the `snippet` object, see http://meta.stackexchange.com/a/242144/134069 --> <script src="http://tjcrowder.github.io/simple-snippets-console/snippet.js"></script> 

问题是您只有一个collection数组,所有对findCombo调用都共享该数组,而shift会使该数组变异。 这意味着,当第一个递归调用findCombo(collection, target - next)清空数组时,第二个递归调用findCombo(collection, target)将发现(非常相同)数组为空,尽管调用者并不打算这样做那。 通过使用slice ,该函数不会损害分配给它的数组。

您可以通过在递归调用之后将数组恢复为其原始值来避免此问题:

var next = collection[0];
collection.shift();
var res = findCombo(collection, target - next) || findCombo(collection, target);
collection.unshift(next);
return res;

但这有点难看。 更好的主意是对要尝试的下一个位置使用额外的index参数,而根本不要变异或克隆数组:

var next = collection[try];
return findCombo(collection, target - next, try+1) || findCombo(collection, target, try+1);

暂无
暂无

声明:本站的技术帖子网页,遵循CC BY-SA 4.0协议,如果您需要转载,请注明本站网址或者原文地址。任何问题请咨询:yoyou2525@163.com.

 
粤ICP备18138465号  © 2020-2024 STACKOOM.COM