【问题标题】:best way to generate empty 2D array生成空二维数组的最佳方法
【发布时间】:2011-06-27 15:26:15
【问题描述】:

是否有更短、更好的方法来生成“n”长度的二维数组?

var a = (function(){ var i=9, arr=[]; while(i--) arr.push([]); return arr })();

a // [ [],[],[],[],[],[],[],[],[] ]

** 老式的捷径**:

var a = (function(a){ while(a.push([]) < 9); return a})([]);

更新 - 使用 ES2015

Array(5).fill().map(a=>[]); // will create 5 Arrays in an Array
// or
Array.from({length:5}, a=>[])

清空二维数组(更节省内存)

function make2dArray(len){
    var a = [];
    while(a.push([]) < len); 
    return a;
}

function empty2dArray(arr){
    for( var i = arr.length; i--; )
      arr[i].length = 0;
}

// lets make a 2D array of 3 items
var a = make2dArray(3);

// lets populate it a bit
a[2].push('demo');
console.log(a); // [[],[],["demo"]]

// clear the array
empty2dArray(a);
console.log(a); // [[],[],[]]

【问题讨论】:

  • 只有当你把它放在一个函数中:var a = make2D(9);;)
  • 我将它用于网络工作者,每次初始化时都需要一个 2D 空数组
  • 我想知道是否有一些花哨的 EC5 用于此
  • 顺便说一句。较短不一定更好(只是想指出标题和问题主体的差异;))。
  • 您可以通过将数组作为参数而不是声明它来使其更短:var a = (function(a){ while(a.push([]) &lt; 9); return a})([]);

标签: javascript arrays


【解决方案1】:

另一种方式:

for(var a = [];a.length < 10; a.push([])); // semicolon is mandatory here

另一种方式:

var a = []; while(a.push([]) < 10);

这是因为.push() [docs] (specification) 返回数组的新长度。


也就是说,这是“减少代码”的错误方式。创建一个具有有意义名称的专用函数并使用它。你的代码会更容易理解:

function get2DArray(size) {
    size = size > 0 ? size : 0;
    var arr = [];

    while(size--) {
        arr.push([]);
    }

    return arr;
}

var a = get2DArray(9);

阅读代码的频率远高于编写代码的频率。

【讨论】:

  • @vsync:是的,不知何故,我认为我需要与 10 进行比较才能得到 9 个元素。但无论如何,我还喜欢 10 多个 :P ;)
  • 我相信代码应该很小,但在开发过程中记录得很好,并且在生产中它无论如何都会被压缩,所以你可以通过这种方式获得更好的压缩率。
  • 我不知道 'a.push([])' 返回一个数字。这对我来说是新的,push 返回一个数字,这很有趣。
  • @vsync:刚刚将其添加到我的答案中。因为它是这样定义的;)
【解决方案2】:

刚刚发现了另一种ES6用一行表达式的方式:

Array.from({length: N}, () => [])

Array.from(arrayLike[, mapFn[, thisArg]])

有关其实现/polyfill 的更多详细信息⇢ MDN Array.from()

array spread syntax 的帮助下又一个巧妙的解决方案:

[...Array(N)].map(() => [])

【讨论】:

  • 请注意,这不是一个函数调用 bun N + 1,因为您为 Array.from 内部发生的每次迭代调用一次 Array.from() 和 N 次 () =&gt; [] 函数。
【解决方案3】:
Array(cardinality).fill(0).map(function(item) {return [];});

其中基数是您正在查看的项目数。在这种情况下,它将是 9。这实际上是我的一位同事建议的。我认为这很整洁:) 这在 ECMA V6 中有效。文档:Array::fill

【讨论】:

  • 如果你使用的是 ES6,那么应该是:Array(5).fill(0).map(()=&gt; [])
  • @vsync,没错。但是,如果需要,您可以自己定义原型函数并在 ECMA 5 中使用它。就是这样,我暂时就这么做了
  • 我在构建过程中使用了 Babel,所以它可以自动将其转换为 ES5
【解决方案4】:
var a = []; for(var i=0;i<10;i++) { a[i] = []; }

【讨论】:

  • 请发布console.log(a);的输出。我很想知道它是否与发布的 OP 相同。好吧,开个玩笑。 -1 这只是设置长度,但它不初始化任何东西。
  • 这只是设置长度,元素仍然是'未定义'
  • 这不会创建带有空数组的 n 个条目。事实上,console.log 只返回一个 []。
  • 我不确定为什么这被否决了......它返回一个空的二维数组。 JSON.stringify(a) 的输出是 "[[],[],[],[],[],[],[],[],[],[]]"
【解决方案5】:

更短的方式可以是:

for(var i=9,a=[];i>=0;i--){ a.push([]) }

【讨论】:

  • 这和我的一模一样。是的,'for' 比 'while' 字符少..但仍然。
【解决方案6】:
var a = [];
var max_length = 10;
for(var i = 0; i < max_length; ++i){ 
    a[i] = []; 
}

【讨论】:

  • 你还不如for(var i=9, a=[]; i--;){... - 更好
  • @vsync,为什么从九点开始更好?
  • @vsync -- 我添加了一个max_length 参数。
  • 为什么不呢?它的代码少,然后从零开始,然后在循环内添加。它给出了相同的结果
  • @vsync,而不是在您使用 a[i] = [] 时——总是最好从 0 开始
【解决方案7】:
for(var i=9,a=[];i>=0;i--){ a.push([]) }

【讨论】:

  • hmmm..我更喜欢一种更明显的方式,即这是对某些 var..like var 2d = ... 的赋值。
【解决方案8】:

在 ES6 中:

(m, n, initialElementValue) => Array(m).fill(Array(n).fill(initialElementValue))

【讨论】:

  • 这不会创建副本并且会使用相同的数组。因此,例如更改 arr[0][1] 将导致 arr[1][1] 和 arr[2][1] 更改。不过可以that way
【解决方案9】:

var x = 3, y = 5, arr = Array(y).fill();
arr = arr.map(function(){return Array(x).fill(' ')});
console.log(arr);

【讨论】:

  • 您的回答并未提供任何其他人多年前未提及的新信息..
【解决方案10】:

Array.fromArray.from在js中生成二维数组的最佳方法

function twodimension(input) {
  let index = 0,
    sqrt = Math.sqrt(input.length);

  return Array.from({
    length: sqrt
  }, (nothing, i) => Array.from({
    length: sqrt
  }, (nothingTwo, j) => input[index++]))
}

console.log(twodimension('abcdefghijklmnopqrstupwxy'))
console.log(twodimension([1,2,3,4,5,6,7,8,9]))

function input(length, fill) {
  let getNums = length * length;
  let fillNums = 1
  if (fill == 'minus') {
    return Array.from({
      length: length
    }, (nothing, i) => Array.from({
      length: length
    }, (nothingTwo, j) => getNums--))
  } else if (fill == 'plus') {
    return Array.from({
      length: length
    }, (nothing, i) => Array.from({
      length: length
    }, (nothingTwo, j) => fillNums++))
  }
  
  // you can dping snake ladders also with Array.from

  if (fill === 'snakes') {
    return Array.from({
        length: length
      }, (_, one) =>
      Array.from({
        length: length
      }, (_, two) => getNums--)
    ).map((el, i) =>
      i % 2 == 1 && length % 2 == 0 ? el.reverse() :
      i % 2 == 0 && length % 2 == 1 ? el.reverse() : el
    );
  }


}

console.log(input(8, 'minus'))
console.log(input(10, 'plus'))

console.log(input(5, 'snakes'))

您可以使用 Array.from 做任何事情,它易于使用且速度快, 这是 ES6 语法中的新方法

【讨论】:

    猜你喜欢
    • 2021-06-16
    • 2017-10-27
    • 1970-01-01
    • 1970-01-01
    • 2020-01-05
    • 1970-01-01
    • 1970-01-01
    • 1970-01-01
    • 2013-08-19
    相关资源
    最近更新 更多