简体   繁体   English

如何将元素推入3D数组(JavaScript)

[英]How to push elements to a 3D array (Javascript)

I have an object 我有一个对象

1:a
2:b
3:c
4:d
5:e
6:f
7:g
8:h
9:i

I want to make a 3D array, like 我想制作一个3D阵列,例如

[
  [ [a], [b], [c] ],
  [ [d], [e], [f] ],
  [ [g], [h], [i] ]
] 

Is it possible to write a for-loop to push first three letters to an 3D array, than second three letters and third at the end (like in example)? 是否可以编写一个for循环将前三个字母推送到3D数组,而不是后三个字母和末尾的第三个字母(例如示例)?

As per @Andreas comment Does JavaScript Guarantee Object Property Order? 按照@Andreas注释JavaScript是否保证对象属性顺序? .

properties order in objects is not guaranteed. 不能保证对象中的属性顺序。 So, if you need to rely on keyVal order a new step must be done: sorting on Object.keys. 因此,如果您需要依赖keyVal顺序,则必须完成一个新步骤:对Object.keys进行排序

A solution can be based looping on Object.keys and modulus operator in order to group by col or division for a row ordering: 解决方案可以基于Object.keys和模数运算符的循环,以便按col或除法对行排序进行分组:

 var obj = {1: 'a', 2: 'b', 3: 'c', 4: 'd', 5: 'e', 6: 'f', 7: 'g', 8: 'h', 9: 'i'}; var resultByCol = []; var resultByRow = []; var objKeys = Object.keys(obj).sort(function(a, b) { return a - b; }); for (var idx = 0; idx < objKeys.length; idx++) { var newIdx = idx % 3; if (resultByCol[newIdx] === undefined) { resultByCol.push([]); } resultByCol[newIdx].push([obj[objKeys[idx]]]); newIdx = Math.floor(idx / 3); if (resultByRow[newIdx] === undefined) { resultByRow.push([]); } resultByRow[newIdx].push([obj[objKeys[idx]]]); } console.log('Grouped by Col: ['); for (var i = 0; i < resultByCol.length; i++) { console.log('\\t' + JSON.stringify(resultByCol[i]) + (((i + 1) == resultByCol.length) ? '' : ',')); } console.log(']'); console.log('Grouped by Row: ['); for (i = 0; i < resultByRow.length; i++) { console.log('\\t' + JSON.stringify(resultByRow[i]) + (((i + 1) == resultByRow.length) ? '' : ',')); } console.log(']'); 

You can first sort array of Object.keys() and then use reduce() to create new array by each 3 keys. 您可以先对Object.keys()数组排序,然后使用reduce()每3个键创建一个新数组。

 var obj = {1: 'a',2: 'b',3: 'c',4: 'd',5: 'e',6: 'f',7: 'g',8: 'h',9: 'i',} var result = Object.keys(obj).sort((a, b) => a - b).reduce(function(r, e, i) { if(i % 3 == 0) r.push([]); r[r.length - 1].push([obj[e]]) return r; }, []) console.log(result) 

This can be achieved very quickly and efficiently using keys and a simple for loop to keep your code expedient. 使用keys和简单的for循环可以非常快速有效地实现此目的for以使您的代码更方便。

@gaetanoM's solution will work just fine, but for a more performant function you can do the following: @gaetanoM的解决方案可以很好地工作,但是对于更高性能的功能,您可以执行以下操作:

var object = {1:'a', 2:'b', 3:'c', 4:'d', 5:'e', 6:'f', 7:'g', 8:'h', 9:'i'};
var keys = Object.keys(object);
var result = [];
for ( var i=, j=keys.length; i<j; i++){
    result[i] = object[keys[i]];
}

Yes. 是。 There are a number of ways to do it. 有很多方法可以做到这一点。 Probably the cleanest looking would be to use the reduce() function: 看起来最干净的可能是使用reduce()函数:

 const obj = { 1: 'a', 2: 'b', 3: 'c', 4: 'd', 5: 'e', 6: 'f', 7: 'g', 8: 'h', 9: 'i' }; const width = 3; // how many in each sub array. const result = Object.keys(obj).map(key => obj[key]) // ['a', 'b', 'c', 'd', 'e', 'f', 'g', 'h'] .reduce((result, v) => { if (result[result.length - 1].length === width) { result.push([v]); // add new row } else { result[result.length - 1].push(v); // add to last row } return result; }, [[]]); console.log(result); 

This is a little more verbose then it needs to be, but more understandable. 这比它需要的更加冗长,但是更容易理解。

First, I loop through and map() the object to a normal array. 首先,我遍历对象并将map()到普通数组。

Then, in the reduce() function, I start it with the first level of nested arrays. 然后,在reduce()函数中,从第一层嵌套数组开始。 Then on each loop, I check the length of the last array in result. 然后在每个循环中,我检查结果中最后一个数组的长度。 If it's full, I add a new array for the next row. 如果已满,则为下一行添加一个新数组。 Otherwise, I just add the value to the last row. 否则,我只需将值添加到最后一行。

A more compact version would be: 一个更紧凑的版本是:

 const obj = { 1: 'a', 2: 'b', 3: 'c', 4: 'd', 5: 'e', 6: 'f', 7: 'g', 8: 'h', 9: 'i' }; const width = 3; const result = Object.keys(obj).reduce((r, k) => r.concat( r[r.length - 1].length === width ? [[obj[k]]] : [r.pop().concat(obj[k])] ), [[]]); console.log(result); 

This example makes more use of .concat() so everything is technically on one line, though obviously it's a good bit harder to read and understand. 这个示例更多地使用了.concat()因此从技术上讲所有内容都在一行上,尽管显然很难阅读和理解。

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

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