递归地将数组元素放在它们自己的数组中

时间:2015-09-08 14:24:46

标签: javascript arrays recursion

我试图创建一个函数,以递归方式将每个数组元素放在自己的数组中。

我认为我的基本情况是正确的,但我的递归调用似乎并没有起作用。任何见解?

function ownList(arr){
  if (arr.length === 1) {
    arr[0] = [arr[0]];
    return;
  } else {
    return arr[0].concat(ownList(arr.slice(1)));
  }    
}
var arr = [1,2,3]
console.log(ownList(arr))// returns []
//should return [[1],[2],[3]]

我试图将每一对放入其自己的列表中(仅递归)。以下代码是正确的(更新)

function ownListPair(arr){
  if (arr.length === 0)
    return arr;
  else if(arr.length === 1)
    return [[arr[0], 0]];
  else 
    return [[arr[0], arr[1]]].concat(ownListPair(arr.slice(2)));
}

// var arr = [3,6,8,1,5]
var arr = [2,7,8,3,1,4]
//returns [ [ 2, 7 ], [ 8, 3 ], [ 1, 4 ]]
console.log(ownListPair(arr))

5 个答案:

答案 0 :(得分:4)

我更喜欢这个解决方案有几个原因:

function ownList(a) {
  return a.length == 0
      ? []
      : [[a[0]]].concat(ownList(a.slice(1))) 
}
  • 它更短更简洁
  • 它也适用于空数组
  • 实际换行只在最后一行发生一次。不必按照他人的建议单独处理length == 1

答案 1 :(得分:1)

将长度为0的情况更为合适。然后你必须得到正确的括号。 concat左侧的东西应该是一个由包含第一个元素的数组组成的数组。

function ownList(arr) {
  return arr.length ? [[arr[0]]].concat(ownList(arr.slice(1))) : [];
}

这是另一种选择,请选择:

function ownList(arr) {
  return arr.length ? [[arr.shift()]] . concat(ownList(arr)) : [];
}

使用一点ES6魔法来提高可读性:

function ownList([head, ...tail]) {
  return head === undefined ? [] : [[head]] . concat(ownList(tail));
}

这里[head, ...tail]正在使用参数解构,它将参数分成第一个元素(头部)和一个剩余部分(尾部)数组。

您也可以使用数组构造函数代替concat

function ownList([head, ...tail]) {
  return head === undefined ? [] : Array([head], ...ownList(tail));
}

答案 2 :(得分:0)

我认为你的基本假设是错误的。你需要做的是检查数组中的每个项是否是一个数组,如果不是只是将项添加到新数组中,如果有,那么函数在数组项上运行。

这是递归。

这段代码做了那种递归......

function ownList(arr)
{
    var newArr = [];
    var length = arr.length;

    for (var i = 0; i < length; i++) {
        if (typeof(arr[i]) === 'object') {
            newArr.push(ownList(arr[i]));
            continue;
        }

        newArr.push([arr[i]]);
    }

    return newArr;
}

var arr = [1, 2, 3];
console.log(ownList(arr));

答案 3 :(得分:0)

这样的事情会起作用吗?

var arr = [1, 2, 3, ["a", "b", "c", ["str"]]], 
result = [];

function flatten(input){

  input.forEach(function(el){
    if(Array.isArray(el)){
      flatten(el)
    }else{
      result.push([el]);
    }
  });

}

flatten(arr);
console.log(JSON.stringify(result));
//[[1],[2],[3],["a"],["b"],["c"],["str"]]

JSBIN

编辑:

var result = [];
function flatten(input){
  if (input.length === 0){
    console.log( "result", result ); //[[1],[2],[3],["a"],["b"],["c"],["str"]]
    return;
  }
  //if zeroth el of input !array, push to result
  if (!Array.isArray(input[0])){
    result.push(input.splice(0, 1));
    flatten(input);  
  }else{
    flatten(input[0]); //else, give input[0] back to flatten
  }
}

window.onload = function(){
  var arr = [1, 2, 3, ["a", "b", "c", ["str"]]];
    flatten(arr); 
}

JSBIN

答案 4 :(得分:0)

今天经历了这一努力之后,事实证明这有效:)

function ownList(arr){
  //base case:

  if (arr.length === 1) {
    return [arr];
  }

 //recurse
 //have to do two brackets here --> (arr.slice(0,1)) since length > 1
  return [arr.slice(0,1)].concat(ownList(arr.slice(1)));

}

var arr = [1,2,3]
console.log(ownList(arr))// returns [[1],[2],[3]]