Convertir un objeto JS a una matriz usando jQuery

417

Mi aplicación crea un objeto JavaScript, como el siguiente:

myObj= {1:[Array-Data], 2:[Array-Data]}

Pero necesito este objeto como una matriz.

array[1]:[Array-Data]
array[2]:[Array-Data]

Así que intenté convertir este objeto en una matriz iterando a $.eachtravés del objeto y agregando el elemento a una matriz:

x=[]
$.each(myObj, function(i,n) {
    x.push(n);});

¿Hay una mejor manera de convertir un objeto en una matriz o tal vez una función?

El bndr
fuente
1
¿Deberían los índices de la matriz ser los mismos que las claves en el objeto original? El primer índice en una matriz siempre es 0, pero su propio código y la mayoría de las respuestas (incluida la aceptada) parecen ignorarlo; aún así, ha revertido mi edición al resultado de ejemplo deseado.
Imre
1
Sí, tiene razón: el primer elemento Array comienza con 0. Pero revertí su edición, porque en mi opinión no era coherente mantener ese ejemplo lo más simple posible, porque cambiar myObj= {1:[Array-Data]a myObj= {0:[Array-Data]no era parte de su edición (como recuerdo bien)
The Bndr
3
Utilice el comando jQuery $ .makeArray (obj) para esa api.jquery.com/jQuery.makeArray
DevlshOne
@DevlshOne la documentación que proporcionó dice: "Convierta un objeto jQuery en una matriz" No creo que esto se ajuste a la pregunta OP
Alex

Respuestas:

429
var myObj = {
    1: [1, 2, 3],
    2: [4, 5, 6]
};

var array = $.map(myObj, function(value, index) {
    return [value];
});


console.log(array);

Salida:

[[1, 2, 3], [4, 5, 6]]
Dogbert
fuente
8
@Dogbert, ¿podrías explicarme el $.map? Cada búsqueda que intento hacer en esto solo muestra muchos enlaces a jQuery o al método de mapa de matrices.
crantok
21
D'oh! Ignora mi comentario. No había notado la etiqueta jQuery en esta pregunta.
crantok
8
¿Hay alguna manera de mantener las claves en la nueva matriz? Cada respuesta en el www que veo carece de la conversión de claves.
TD_Nijboer
55
También puede hacer esto sin jQuery: Object.keys (myObject) .map (function (val) {return [val]});
Kris Erickson
3
@TD_Nijboer Sí, use en value.key = index; return [value];lugar dereturn [value];
Simon Arnold
742

Si está buscando un enfoque funcional:

var obj = {1: 11, 2: 22};
var arr = Object.keys(obj).map(function (key) { return obj[key]; });

Resultados en:

[11, 22]

Lo mismo con una función de flecha ES6:

Object.keys(obj).map(key => obj[key])

Con ES7 podrás usar Object.valuesen su lugar ( más información ):

var arr = Object.values(obj);

O si ya está usando Underscore / Lo-Dash:

var arr = _.values(obj)
Joel Richard
fuente
3
Insatisfecho con la respuesta principal, acabo de escribir esta función casi exacta, volví a publicarla como respuesta, me desplacé hacia abajo, vi 170. Realizado, hombre. Si no me hubiera rendido, no habría tenido que pensar :) Esto debería estar en la cima. OP por favor seleccione como respuesta.
j03m
1
para cualquiera para quien esto no sea obvio, las claves no necesitan ser secuenciales (es decir, en este ejemplo son 1 y 2, pero también podrían ser una clave de cadena o un número no secuencial
Simon_Weaver
Para el primer párrafo del código me falta un punto y coma. No estoy seguro de por qué.
JohnnyBizzle
@JohnnyBizzle Supongo que tu linter requiere escribir "return obj [key];" con punto y coma al final. JavaScript no lo hace.
Joel Richard
30

Creo que puede usar for inpero verificando si la propiedad no está heredada

myObj= {1:[Array-Data], 2:[Array-Data]}
var arr =[];
for( var i in myObj ) {
    if (myObj.hasOwnProperty(i)){
       arr.push(myObj[i]);
    }
}

EDITAR: si lo desea, también puede mantener los índices de su objeto, pero debe verificar si son numéricos (y obtiene valores indefinidos para los índices faltantes:

function isNumber(n) {
  return !isNaN(parseFloat(n)) && isFinite(n);
}

myObj= {1:[1,2], 2:[3,4]}
var arr =[];
for( var i in myObj ) {
    if (myObj.hasOwnProperty(i)){
        if (isNumber(i)){
            arr[i] = myObj[i];
        }else{
          arr.push(myObj[i]);
        }
    }
}
Nicola Peluchetti
fuente
1
Deberías haber probado el código. $.mapse aplane Array-Data.
Marko Dumic
tienes razón, no lo probé con una matriz y el mapa lo aplana. modifiqué la respuesta
Nicola Peluchetti
@Nicola Peluchetti $ .makeArray () suena bien, pero no es lo que estaba buscando, porque simplemente coloca el objeto en un elemento de matriz: [{1:[Array-Data], 2:[Array-Data]}]y $.map()tampoco parece exitoso. Parece que todos los datos de la submatriz se fusionan en una matriz. array.lengthdebería devolver 2 (porque existen 2 elementos), pero devuelve 67, que es el número de todos los elementos en todos ["Array-Data"].
The Bndr
@The Bndr publiqué otra solución, pero puedes usar el mapa como lo sugiere dogbert
Nicola Peluchetti
Creo que debe especificar explícitamente el índice de la matriz ... como arr[+i] = myObj[i];porque (i) for(...in...)no garantiza que devuelva propiedades en ningún orden (ii) en el ejemplo de OP, las propiedades comienzan desde 1, no 0.
Salman A
30

Simplemente hacer

Object.values(obj);

¡Eso es todo!

Pila
fuente
11
Object.values ​​es un método ES2017 que no es compatible con Safari, IE, Node 6.
Phil Ricketts
25

Si conoce el índice máximo en su objeto, puede hacer lo siguiente:

var myObj = {
    1: ['c', 'd'],
    2: ['a', 'b']
  },
  myArr;

myObj.length = 3; //max index + 1
myArr = Array.prototype.slice.apply(myObj);
console.log(myArr); //[undefined, ['c', 'd'], ['a', 'b']]

bjornd
fuente
1
Sería mucho mejor que el código que está generando el objeto también establezca la longitud o, de hecho, lo convierta en una matriz. No espero que ninguno sea posible, por lo que esta respuesta para mí no es útil.
user2000095-tim
myObj.length = Object.keys(myObj).length
calvas
19

Dado que ES5 Object.keys () devuelve una matriz que contiene las propiedades definidas directamente en un objeto (excluyendo las propiedades definidas en la cadena del prototipo):

Object.keys(yourObject).map(function(key){ return yourObject[key] });

ES6 va un paso más allá con las funciones de flecha:

Object.keys(yourObject).map(key => yourObject[key]);
Maxdow
fuente
1
Para el ES5 actual (aunque disfruto del ES6): Object.keys (yourObject) .map (function (key) {return yourObject [key]});
David Zorychta
18

Hoy en día, hay una manera simple de hacer esto: Object.values ​​() .

var myObj = {
    1: [1, 2, 3],
    2: [4, 5, 6]
};

console.log(Object.values(myObj));

Salida:

[[1, 2, 3], [4, 5, 6]]

Esto no requiere jQuery, se ha definido en ECMAScript 2017.
Es compatible con todos los navegadores modernos (olvídate de IE).

Stopi
fuente
si hago algo como var state = { ingredient: { salad: 1, bacon: 1, } }y luego var HariOm = Object.values(state);seguido console.log(typeof HariOM), muestra el tipo como un objeto. ¿No debería mostrarlo como una matriz?
iRohitBhatia
Eso es completamente normal, consulte la referencia aquí: developer.mozilla.org/en-US/docs/Web/JavaScript/Reference/… - Puede usarArray.isArray(HariOM)
Stopi
16

El mejor método sería usar una función solo de javascript:

var myArr = Array.prototype.slice.call(myObj, 0);
Friedrich
fuente
@Qwerty qué navegador?
test30
Cromo. Probado convar myObj = {1:[1,2,3],2:[4,5,6]};
Qwerty
Tenga en cuenta que este método funciona para convertir "objetos tipo matriz", lo que significa que deben tener una propiedad de "longitud" y propiedades enumeradas contando desde 0. Entonces, para que el ejemplo de @ Qwerty funcione, intente esto: {0: [1 , 2,3], 1: [4,5,6], longitud: 2}. Experimente con valores de índice y valores de longitud, es un poco indulgente. Aquí hay una buena lectura sobre el tema: nfriedly.com/techblog/2009/06/… Salte a "Objetos tipo matriz".
Matt
15
x = [];
for( var i in myObj ) {
    x[i] = myObj[i];
}
nadie
fuente
10
Deberías usar push, de lo contrario podrías terminar creando un objeto
Nicola Peluchetti
Tal vez es una fuerza mejor para int el índice. var bbb = {'1': 'a', '3': 'b'}; var x = []; for (var i in bbb) { x[parseInt(i)] = bbb[i];} console.log(x);
tres.14159
15

ECMASCRIPT 5:

Object.keys(myObj).map(function(x) { return myObj[x]; })

ECMASCRIPT 2015 o ES6:

Object.keys(myObj).map(x => myObj[x])
Aditya Singh
fuente
13

Qué tal si jQuery.makeArray(obj)

Así es como lo hice en mi aplicación.

Sankalp Singha
fuente
2
Esto devuelve [Objeto] para el ejemplo anterior.
Kris Erickson
1
solo es cuestión de agregar [0] índice y me salvaste la vida :)
Raheel
6

La resolución es muy simple.

var my_obj = {1:[Array-Data], 2:[Array-Data]}
Object.keys(my_obj).map(function(property_name){ 
    return my_obj[property_name]; 
});
Ivan Fretes
fuente
3

Fiddle Demo

Extensión a respuesta de bjornd .

var myObj = {
    1: [1, [2], 3],
    2: [4, 5, [6]]
}, count = 0,
    i;
//count the JavaScript object length supporting IE < 9 also
for (i in myObj) {
    if (myObj.hasOwnProperty(i)) {
        count++;
    }
}
//count = Object.keys(myObj).length;// but not support IE < 9
myObj.length = count + 1; //max index + 1
myArr = Array.prototype.slice.apply(myObj);
console.log(myArr);


Referencia

Array.prototype.slice ()

Function.prototype.apply ()

Object.prototype.hasOwnProperty ()

Object.keys ()

Tushar Gupta - curioustushar
fuente
Podría estar equivocado, pero ¿debería ser mejor que myObj sea enumerable a partir de 0? De lo contrario, me parece que tenemos un problema en el que nuestra matriz sería: [undefined, [1, [2], 3]] (La primera parte no está definida porque no encuentra myObj ['0'] y la última parte myObj ['2'] se expulsa porque después de leer .length se detiene en myObj ['1']
Alex Werner
2

Si desea mantener el nombre de las propiedades del objeto como valores. Ejemplo:

var fields = {
    Name: { type: 'string', maxLength: 50 },
    Age: { type: 'number', minValue: 0 }
}

Utilizar Object.keys(), Array.map()y Object.assign():

var columns = Object.keys( fields ).map( p => Object.assign( fields[p], {field:p} ) )

Resultado:

[ { field: 'Name', type: 'string', maxLength: 50 }, 
  { field: 'Age', type: 'number', minValue: 0 } ]

Explicación:

Object.keys()enumera todas las propiedades de la fuente; .map()aplica la =>función a cada propiedad y devuelve una matriz; Object.assign()combina el nombre y el valor de cada propiedad.

Supersharp
fuente
1

Hice una función personalizada:

    Object.prototype.toArray=function(){
    var arr=new Array();
    for( var i in this ) {
        if (this.hasOwnProperty(i)){
            arr.push(this[i]);
        }
    }
    return arr;
};
mailmindlin
fuente
0

Después de algunas pruebas, aquí hay un objeto general para convertir el convertidor de funciones:

Tienes el objeto:

var obj = {
    some_key_1: "some_value_1"
    some_key_2: "some_value_2"
};

La función:

function ObjectToArray(o)
{
    var k = Object.getOwnPropertyNames(o);
    var v = Object.values(o);

    var c = function(l)
    {
        this.k = [];
        this.v = [];
        this.length = l;
    };

    var r = new c(k.length);

    for (var i = 0; i < k.length; i++)
    {
        r.k[i] = k[i];
        r.v[i] = v[i];
    }

    return r;
}

Uso de funciones:

var arr = ObjectToArray(obj);

Usted obtiene:

arr {
    key: [
        "some_key_1",
        "some_key_2"
    ],
    value: [
        "some_value_1",
        "some_value_2"
    ],
    length: 2
}

Entonces puede alcanzar todas las claves y valores como:

for (var i = 0; i < arr.length; i++)
{
    console.log(arr.key[i] + " = " + arr.value[i]);
}

Resultado en la consola:

some_key_1 = some_value_1
some_key_2 = some_value_2

Editar:

O en forma de prototipo:

Object.prototype.objectToArray = function()
{
    if (
        typeof this != 'object' ||
        typeof this.length != "undefined"
    ) {
        return false;
    }

    var k = Object.getOwnPropertyNames(this);
    var v = Object.values(this);

    var c = function(l)
    {
        this.k = [];
        this.v = [];
        this.length = l;
    };

    var r = new c(k.length);

    for (var i = 0; i < k.length; i++)
    {
        r.k[i] = k[i];
        r.v[i] = v[i];
    }

    return r;
};

Y luego usar como:

console.log(obj.objectToArray);
Kostas
fuente
0

Se puede crear una función simple de hacer la conversión de objecta array, algo como esto puede hacer el trabajo para usted usando javascript puro:

var objectToArray = function(obj) {
  var arr = [];
  if ('object' !== typeof obj || 'undefined' === typeof obj || Array.isArray(obj)) {
    return obj;
  } else {
    Object.keys(obj).map(x=>arr.push(obj[x]));
  }
  return arr;
};

o este:

var objectToArray = function(obj) {
  var arr =[];
  for(let o in obj) {
    if (obj.hasOwnProperty(o)) {
      arr.push(obj[o]);
    }
  }
  return arr;
};

y llame y use la función de la siguiente manera:

var obj = {1:'a', 2:'b', 3:'c', 4:'d', 5:'e'};
objectToArray(obj); // return ["a", "b", "c", "d", "e"]

También en el futuro tendremos algo llamado Object.values(obj), similar al Object.keys(obj)cual devolverá todas las propiedades para usted como una matriz, pero aún no es compatible con muchos navegadores ...

Alireza
fuente