32

How to get the dimensions given a multidimensional array?
Edit: it could be of 1, 2, or 3 dimensions but each sub-array has the same length.

i.e. for

var a = [[1,1,1], [1,1,1]]

would be [2,3]

3
  • what is sub lists are different sizes? Commented Apr 19, 2012 at 22:21
  • So far, this is the best answer I've found: stackoverflow.com/a/13814933/975097 Commented Dec 12, 2012 at 0:03
  • Ever since .reduce() got added to the Array prototype, this has been a one-liner both for fixed inner length (const dimensions = [a.length, a[0].length]) as well as uneven length (const dimensions = [a.length, a.reduce((t,e) => Math.max(t, e.length), 0)]). The latter yielding the same answer as the first for stably sized input. Commented Sep 30, 2020 at 17:22

11 Answers 11

39
const dimensions = [ arr.length, arr[0].length ];

This works, if you know length of the inner arrays never change.


If the dimension of the inner arrays aren't static (jagged array), you could combine Array.reduce and Math.max to calculate the largest dimension:

const dimensions = [
    arr.length,
    arr.reduce((x, y) => Math.max(x, y.length), 0)
];
Sign up to request clarification or add additional context in comments.

4 Comments

"["+arr.length+","+arr[0].length+"]" :)
function arraySize(arr){return {c: arr.length, r:arr[0].length === undefined?1:arr[0].length };}
or, for uneven inner dimensions: dimensions = [ a.length, a.reduce((t,e) => Math.max(t, e.length), 0) ];
For the former, I'm afraid you forgot the possibility of arr.length == 0, thus causing ArrayIndexOutOfBound or something
10

Considering that sub lists can have different size, get the minimum size or depending on need make it max

function size(ar){
    var row_count = ar.length;
    var row_sizes = []
    for(var i=0;i<row_count;i++){
        row_sizes.push(ar[i].length)
    }
    return [row_count, Math.min.apply(null, row_sizes)]
}
size([[1, 1, 1], [1, 1, 1]])

Output:

[2, 3]

2 Comments

Would this work for arrays of any dimension, or just for two-dimensional arrays?
@AndersonGreen it is only for two dimensional, but a recursive call should make it work for N dimesnions
6

Getting the number of elements of multi-dimensional arrays is as simple as this...

var Size = a.join(',').split(',').length;

3 Comments

Hi. Try to elaborate as to why your solution work.
That seems to be the shortest way doing it, thanks
@NisanthReddy: the join() concats all elements regardless of array dimension separated by "," chars, then the split separates them at the "," chars deleting them, leaving just a 1D array of all the elements, whose length is reported. However the this will fail if any element(s) contain one or more "," chars in their value. This is true of any separating char used, so the best bet is to use a random string joiner/splitter like Math.random().toString(36)+Math.random().toString(36) .
5

This works for whatever dimension (supposing that each sub array has the same length):

function getDim(a) {
    var dim = [];
    for (;;) {
        dim.push(a.length);

        if (Array.isArray(a[0])) {
            a = a[0];
        } else {
            break;
        }
    }
    return dim;
}

Comments

2
var dim = [
    a.length,
    a[0].length
];

This should work, given that each sub array is the same length, however, if thats not the case, you might want to do something like:

function findDim(a){
    var mainLen = 0;
    var subLen = 0;

    mainLen = a.length;

    for(var i=0; i < mainLen; i++){
        var len = a[i].length;
        subLen = (len > subLen ? len : subLen);
    }

    return [mainLen, subLen];
};

Comments

2

Also you can do a recursive function to calculate the shape of an array assuming all the dimensions are identical:

arrayShapeRecursive = arr => {
  return arr.length ? [...[arr.length], ...arrayShapeRecursive(arr[0])] : [];
}

Comments

1

this function will check if the array is valid (not a scalar nor a string) and if the elements of that array are valid (they have the same length) then give the dimensions if all conditions are satisfied or throw an error if else.


function getDim(x){
    dim=[]
    try {
        // throw error if the passed variable is a string or a scalar
        if((isFinite(x) && !x.length) || typeof(x)=='string') throw  'This is a scalar or a string  not an array!';
        // loop over the array to extract length of each element.
        // if we get an element that is not an array, return the found dimensions 
        while (x){

            dim.push(x.length)
            currentLevel=x
            x=Array.isArray(x[0])?x[0]:false;
            // check if all elements of the array are of equal dimention. If not, throw an error
            ans=currentLevel.every((value,index,arr)=>{ return value.length==x.length}) ;
            if(!ans) throw 'elements of the array are not of equal dimension !'

        }
        return dim
    } catch (error) {
        return error 
    }
}

Comments

1

In your case you can simply use arr.length and arr[0].length to find the width and the depth.

Often, the arrays will have variable depths which makes it necessary to iterate through the entire array using recursion.

I created a prototype method of Object to get determine how deep the array is. To use it simply call myArray.dimensionsDeep(). It works for both Objects and Arrays.

Object.prototype.isMultidimensional = function()
{
    return this.constructor.name !== "String" && Object.keys(this).some((i) => { return this[i].length > 0; });
}

Object.prototype.dimensionsDeep = function()
{
    if (typeof Object.dimensions === 'undefined')
    {
        if (!this.length)
            return 0;
        Object.dimensions = 0;
        Object.currentLevel = 0;
    }
    Object.keys(this).forEach((i) =>
    {
        if (this[i].isMultidimensional())
        {
            Object.currentLevel++;
            if (Object.currentLevel > Object.dimensions)
                Object.dimensions = Object.currentLevel;
            this[i].dimensionsDeep();
        }
    });
    Object.currentLevel--;
    if (Object.currentLevel < 0)
    {
        delete(Object.currentLevel);
        var temp = Object.dimensions;
        delete(Object.dimensions);
        return temp + 1;
    }
}

Comments

0
var a = [[1,1,1], [1,1,1]];
var size=[];
while(s=a.pop) size.push(s.length);

Or if you want to have the length inside a:

var a = [[1,1,1], [1,1,1]];
for(i in a) a[i]=a[i].length;

Edit: I apologize, I wasn't in the subject. The following code calculate max row and column for a two dimensional array.

var innerSize = 0, i=0, l=a.length, l2;
for(;i<l;i++) if(innerSize<(l2=a[i].length)) innerSize = l2
[l, innerSize]

You can change the < to > if you want the minimum size.

Comments

0
//// From https://gist.github.com/srikumarks/4303229 ////
// Assumes a valid matrix and returns its dimension array.
// Won't work for irregular matrices, but is cheap.
function dim(mat) {
    if (mat instanceof Array) {
        return [mat.length].concat(dim(mat[0]));
    } else {
        return [];
    }
}

All credit to https://gist.github.com/srikumarks

Comments

0

Here you go; the code below works for any dimensional matrix/array.

function getMatrixDimensions(matrix, dimensions = []) {
  if (Array.isArray(matrix)) {
    dimensions.push(matrix.length);
    return getMatrixDimensions(matrix[0], dimensions);
  } else return dimensions;
}

// Example
console.log(getMatrixDimensions([
  [1, 2, 3],
  [1, 2, 3],
]));

Comments

Your Answer

By clicking “Post Your Answer”, you agree to our terms of service and acknowledge you have read our privacy policy.