Longitud de un objeto en JavaScript: ¿por qué no hay un simple .length y qué hacer?
\n\n¿Alguna vez te has sorprendido pensando: «¿Por qué un array tiene la propiedad .length y un objeto no?». Si es así, no estás solo. La pregunta «Length of a JavaScript object» se encuentra entre las más populares en Stack Overflow con miles de visitas. Y no es de extrañar: todo principiante, tarde o temprano, intenta escribir obj.length y obtiene undefined.
En este artículo, entenderemos por qué sucede esto y, lo más importante, cómo calcular correctamente la longitud de un objeto en JavaScript. Conocerás 4 formas prácticas, comprenderás cuándo usar cada una y olvidarás para siempre la confusión con la longitud de un objeto.
\n\n¿Por qué los objetos no tienen la propiedad length?
\n\nTodo se debe a la naturaleza de los objetos. Un array es una colección ordenada con índices numéricos. El motor de JavaScript puede decir fácilmente: «En el array hay 5 elementos». Pero un objeto es un conjunto no ordenado de pares «clave-valor». En teoría, puedes agregar una propiedad, eliminarla, volver a agregarla, y el orden no está garantizado (al menos en especificaciones antiguas).
\n\nPor eso, los objetos simples no tienen un .length incorporado. Pero eso no significa que no podamos calcularlo. Veamos cómo.
Forma n.º 1: Object.keys() — el estándar de oro
\n\nLa forma más popular y recomendada es usar Object.keys(). Este método devuelve un array de las propiedades enumerables propias (no heredadas) del objeto. Y un array, como sabemos, tiene .length.
const user = {\n name: 'Ana',\n age: 28,\n city: 'Madrid',\n isAdmin: false\n};\n\nconst length = Object.keys(user).length;\nconsole.log(length); // 4\n\n¡Ingeniosamente simple! Obtienes un array de claves y luego tomas su longitud. Este método funciona en todos los navegadores modernos y en Node.js.
\n\n¿Qué incluye Object.keys()?
\n\nUn punto importante: Object.keys() devuelve solo las propiedades propias y enumerables. Esto significa que:
- \n
- Propias — no heredadas a través del prototipo. Si creaste un objeto mediante una clase o agregaste un método al prototipo, no aparecerá en el resultado. \n
- Enumerables — aquellas cuyo flag
enumerableestá entrue. Por defecto, todas las propiedades creadas mediante asignación son enumerables. Pero si usasteObject.defineProperty()conenumerable: false, esa propiedad será ignorada. \n
Ejemplo con una propiedad no enumerable:
\n\nconst car = {\n brand: 'Toyota',\n model: 'Camry'\n};\n\nObject.defineProperty(car, 'vin', {\n value: 'JT2BF22KX00000001',\n enumerable: false\n});\n\nconsole.log(Object.keys(car).length); // 2 (vin no se cuenta)\n\nForma n.º 2: Object.values() y Object.entries()
\n\nA veces no necesitas solo la cantidad de claves, sino la cantidad de valores o pares. Aquí te ayudan dos hermanos gemelos:
\n\n- \n
Object.values(obj)— devuelve un array de valores \n Object.entries(obj)— devuelve un array de arrays [clave, valor] \n
Ambos devuelven arrays y, por lo tanto, tienen .length:
const book = {\n title: 'El Maestro y Margarita',\n author: 'Bulgákov',\n year: 1966\n};\n\nconsole.log(Object.values(book).length); // 3\nconsole.log(Object.entries(book).length); // 3\n\nEn esencia, es la misma cantidad, pero Object.entries() proporciona más datos si luego necesitas tanto las claves como los valores.
Forma n.º 3: Bucle for...in (y cómo no caer en una trampa)
\n\nUna forma clásica, pero menos conveniente, es usar el bucle for...in y contar las propiedades manualmente:
const person = {\n name: 'Iván',\n age: 30\n};\n\nlet count = 0;\nfor (let key in