
Decir que en JavaScript “todo es un objeto” es incorrecto… No “todo hereda de Object” en el lenguaje, aunque lo parezca. No s茅 de d贸nde sali贸 esa idea pero… es un error pensar esto.
Tipos de datos en JavaScript
Seg煤n la especificaci贸n de ECMAScript, los tipos de datos disponibles en JavaScript se separan en dos grupos: primitivos y objetos.
Los primitivos son:
undefined
, null
, Boolean
, Number
, String
, BigInt
y Symbol
.
Los primitivos representan un dato en la implementaci贸n m谩s baja posible.
Todo lo que no es un primitivo, es un objeto. No s贸lo el propio Object
. Tambi茅n los Array
, Set
, Map
, Date
, Regex
, Promise
y todo lo que se te ocurra.
Las Function
tambi茅n son objetos. Con la particularidad que pueden ser invocados (ejecutados).
typeof
para salir casi de dudas
Para saber el tipo de dato en JavaScript podemos usar el operador typeof
. De hecho, este operador es el que justamente viene a desmentir que todo sea un objeto aunque tiene algunas particularidades que luego comentaremos.
typeof 2; // number
typeof true; // boolean
typeof "midu"; // string
typeof undefined; // undefined
typeof Symbol(); // symbol
typeof 2n; // bigint
typeof null; //object * (caso especial)
typeof {}; // object
typeof []; // object
typeof new Map(); // object
typeof new Set(); // object
typeof /abc/; // object
Como podemos ver, los tipos primitivos indican su tipo esperado… excepto null
. En este caso, el tipo es object
. Esto es por un bug hist贸rico en el lenguaje que no se ha solucionado para no romper la retro compatibilidad con c贸digo ya existente. Lo correcto ser铆a que el typeof
diese null
, ya que se trata de un tipo primitivo, tal y como indica la especificaci贸n..
Existe otro caso especial. Las funciones. Tienen su propio typeof
, ya que son un caso especial de object
ya que son llamables (ejecutables).
typeof function () {} // function
null por un error hist贸rico tiene como typeof object. Pero no es que sea un object ni que herede de 茅l. No se arregla el bug para evitar problemas de retrocompatibilidad. Es lo que tiene la web.
Boxing de tipos primitivos
驴D贸nde viene entonces la confusi贸n de que todo es un objeto en JavaScript? La confusi贸n viene porque los primitivos parecen tener propiedades y m茅todos.
Por ejemplo, puedes acceder a la longitud de un objeto o transformar un n煤mero en un string con decimales:
"Esto es un primitivo".length // 20
"Esto tambi茅n".toUpperCase() // 'ESTO TAMBI脡N'
(2).toString() // '2'
(2).toFixed(2) // '2.00'
true.toString() // 'true'
true.valueOf() // true
Lo que ocurre es que JavaScript envuelve el tipo primitivo autom谩ticamente. Aunque en la especificaci贸n no habla de un t茅rmino en concreto, se le conoce como boxing y ser铆a, seg煤n la especificaci贸n, una forma de coerci贸n implicita para transformar el dato primitivo en objeto al vuelo.
Aunque creas que la coerci贸n s贸lo es para transformar de un tipo a otro, grandes autores como Kyle Simpson consideran que este “boxing” tambi茅n ser铆a una coerci贸n al ser una transformaci贸n autom谩ticamente del lenguaje.
As铆 que la confusi贸n viene por pensar que el primitivo de string es lo mismo que la instancia de usar el objeto String que nos da autom谩ticamente JavaScript para facilitarnos la vida.
const n = 2
typeof n // number
n instanceof Number // false
const n2 = new Number(2)
typeof n2 // number
n2 instanceof Number // true
n === n2 // false
Y no lo es. No son iguales, ni son del mismo tipo. Y, claro, el primero no hereda de object
.
"hola" === new String("hola") // false
2 === new Number(2) // false
true === new Boolean(true) // false
Ojo. No confundas usar el new Boolean(true)
con simplemente usar Boolean(true)
. El primero crea una instancia del objeto Boolean y el segundo s贸lo hace una conversi贸n del par谩metro al tipo primitivo boolean
.
true === Boolean(true) // true
true === Boolean(1) // true
true === Boolean(true) // true
Los objetos son una parte MUY importante en JavaScript pero eso no significa que TODO sea un objeto.
Conclusiones
Por la coerci贸n de datos, o el boxing que hemos visto, puede parecer todo es un objeto, ya que simula que podemos acceder a propiedades y m茅todos de un primitivo.
En realidad es JavaScript simplificando su sintaxis para que no tengas que hacerlo tu mismo. Es obvio que los tipos primitivos no son objetos, ya que, si lo fuesen, sus valores ser铆an mutables tambi茅n (y no lo son).
Esto es en JavaScript… hay que tener en cuenta que en otros lenguajes de programaci贸n esto puede ser diferente. 隆Tenlo en cuenta!