简体   繁体   English

将值存储在多维数组中(JavaScript)

[英]Storing value in a multidimensional array (Javascript)

What is the quickest way to store a value in an array at position, let's say, [30][1][0] ... 将位置值存储在数组中的最快方法是什么,比如[30] [1] [0] ...

I tried var myArray[30][1][0] = new Date(); 我尝试了var myArray[30][1][0] = new Date(); but it won't work without doing var myArray = []; myArray[30] = []; myArray[30][1] = []; 但是如果不做var myArray = []; myArray[30] = []; myArray[30][1] = [];就无法工作var myArray = []; myArray[30] = []; myArray[30][1] = []; var myArray = []; myArray[30] = []; myArray[30][1] = []; beforehand. 预先。

What am I doing wrong? 我究竟做错了什么?

EDIT: My issue is that I don't know, first, if the variable myArray already exists and, second, if there's already a value at position, let's say, [29][2][15], which I wouldn't want to overwrite. 编辑:我的问题是,我不知道,首先,变量myArray是否已经存在,其次,如果位置上已经有一个值,可以说[29] [2] [15],我不会要覆盖。

The correct way to do what you want would be: 做您想要做的正确方法是:

var array = [[[new Date()]]];

However, the resulting multidimensional array will not have exactly 30 elements on the third dimension and 1 on the second, like you had in your original code. 但是,生成的多维数组将不会像原始代码中那样在第三个维度上恰好包含30个元素,在第二个维度上恰好具有1个元素。 Not sure if that's going to be a problem for you. 不知道这是否会对您造成问题。

When you do myArray[30][1][0] , JavaScript is trying to access element 30 in the array myArray , but, since myArray variable was not initialized to anything yet, it has the value undefined . 当您执行myArray[30][1][0] ,JavaScript试图访问数组myArray中的元素30,但是,由于myArray变量尚未初始化为任何值,因此其值是undefined So your code is equivalent with: 因此,您的代码等效于:

var myArray;
myArray[30] = new Date();

This code is going to issue the error Cannot set property '30' of undefined . 此代码将发出错误Cannot set property '30' of undefined

Edit: If you want to make sure the array exists before assigning values and avoid overriding existing values, the most elegant way I can think of is: 编辑:如果要在分配值之前确保数组存在并避免覆盖现有值,我能想到的最优雅的方法是:

// Store a value in the array, at index (posX, posY, posZ), only if
// that position in the array is currently empty
function storeDateNoOverride(theArray, posX, posY, posZ, date) {
    var theArray = theArray || [];
    theArray[posX] = theArray[posX] || [];
    theArray[posX][posY] = theArray[posX][posY] || [];
    theArray[posX][posY][posZ] = theArray[posX][posY][posZ] || date;
}

// If variable theArray doesn't have a value yet, assign it to a new array
var theArray = theArray || [];

storeDateNoOverride(theArray, 30, 1, 0, new Date());

What is the quickest way to store a value in an array at position, let's say, [30][1][0] ... 将位置值存储在数组中的最快方法是什么,比如[30] [1] [0] ...

The classic way is 经典的方法是

array[30] = array[30] || [];
array[30][1] = array[30][1] || [];
array[30][1][0] = array[30][1][0] || [];
array[30][1][0].push(value);

or the equivalent in suitably parameterized fashion. 或以适当参数化方式进行的等效操作。

You could make a little helper: 您可以帮一点忙:

function subarray(array, n) {
  return array[n] = array[n] || [];
}

Then you could write 那你可以写

subarray(subarray(subarray(array, 30), 1), 0).push(value)

You could also write the helper to do all the accessing and checking in one fell swoop: 您还可以编写帮助程序来完成所有访问和检查操作:

function getNestedElement(array, firstIndex, ...indices) {
  if (firstIndex === undefined) return array;
  return getNestedElement(array[firstIndex] = array[firstIndex] || [], ...indices);
}

And then write 然后写

getNestedElement(array, 30, 1, 0).push(value)

You can not initialize a nested object like that. 您不能像这样初始化嵌套对象。 There are two ways. 有两种方法。 If you know your ND array size in advance you should first instantiate it as follows; 如果您事先知道ND数组的大小,则应首先按以下方式实例化它;

 Array.prototype.clone = function(){ return this.map(e => Array.isArray(e) ? e.clone() : e); }; function arrayND(...n){ return n.reduceRight((p,c) => c = (new Array(c)).fill().map(e => Array.isArray(p) ? p.clone() : p )); } var arr = arrayND(5,5,5,void 0); // create 5x5x5 array and fill each cell with "undefined" arr[3][2][1] = arr[3][2][1] || new Date(); // if falsey value then insert current date. console.log(arr); 

However if you don't know the multidimensional size in advance and would like to grow your array dynamically you can use a function like getNestedValue() and setNestedValue() . 但是,如果您事先不知道多维尺寸,并且想动态增长数组,则可以使用类似getNestedValue()setNestedValue()的函数。 In this particular case i will extend the Object.prototype . 在这种情况下,我将扩展Object.prototype In production code this should be done through Object.defineProperty() tool though. 在生产代码中,这应该通过Object.defineProperty()工具完成。

 Object.prototype.getNestedValue = function(...a) { return a.length > 1 ? (this[a[0]] !== void 0 && this[a[0]].getNestedValue(...a.slice(1))) : this[a[0]]; }; Object.prototype.setNestedValue = function(...a) { a.length > 2 ? typeof this[a[0]] === "object" && this[a[0]] !== null ? this[a[0]].setNestedValue(...a.slice(1)) : (this[a[0]] = typeof a[1] === "string" ? {} : new Array(a[1]), this[a[0]].setNestedValue(...a.slice(1))) : this[a[0]] = a[1]; return this; }; var arr = []; arr.getNestedValue(30,1,0) || arr.setNestedValue(30,1,0,new Date()); // if exists don't overwrite it; console.log(arr[30][1][0]); 

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

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