Pular para o conteúdo
Cursos

DevClub

LógicaFront-endBack-endMobile

IA Club

IA na prática
Estudar programaçãoEstudar IA
LiçãoIniciantecódigo testado

Arrays em JavaScript: criar, ler e entender por dentro

Array em JavaScript é um objeto com chaves numéricas — por isso typeof devolve object, existem buracos e índice fora do range volta undefined, não erro.

Rodolfo Mori7 min de leitura

Array é uma estrutura de dados que mantém valores em uma sequência. Você cria a lista com colchetes, acessa cada item por um índice que começa em zero e consulta a quantidade de posições com .length.

Imagine um armário com compartimentos numerados. O array é o armário, cada índice é o número de uma porta e o valor é o que está guardado ali. Abrir a porta 0 entrega o primeiro item; pedir uma porta que não existe não derruba o armário, apenas devolve undefined. No JavaScript, porém, esses números são chaves de um objeto com comportamento especial — e não compartimentos físicos.

Esse detalhe explica por que typeof devolve 'object', por que existe Array.isArray, como surgem posições vazias e por que o undefined de um índice inválido costuma causar erro apenas algumas linhas depois.

Todos os exemplos são da mesma loja virtual que aparece em variáveis em JavaScript: carrinho, produto, pedido.

Criar um array e ler pelo índice

js
const carrinho = ['Teclado mecânico', 'Mouse sem fio', 'Headset'];

console.log(carrinho[0]);
console.log(carrinho[2]);
console.log(carrinho.length);
console.log(carrinho);
Teclado mecânico Headset 3 [ 'Teclado mecânico', 'Mouse sem fio', 'Headset' ]

Três itens, índices 0, 1 e 2. O último índice é sempre length - 1 — o erro de somar um a mais aqui tem nome próprio em inglês, off-by-one, e é responsável por boa parte dos undefined que você vai caçar na vida.

Por que typeof diz “object”

js
const precos = [289.9, 149.9, 399];

console.log(typeof precos);
console.log(typeof precos[0]);
console.log(Array.isArray(precos));
console.log(Object.keys(precos));
console.log(precos['1']);
object number true [ '0', '1', '2' ] 149.9

Olhe a penúltima linha: as chaves do array são as strings '0', '1' e '2'. E a última prova o outro lado: precos['1'] funciona igual a precos[1], porque o motor converte o índice para string antes de procurar.

Array não é um tipo primitivo do JavaScript. É um objeto com um comportamento especial ligado às chaves numéricas e ao length. Por isso typeof nunca vai te ajudar a distinguir um array de um objeto comum — e por isso existe Array.isArray, que é a checagem correta.

Dá para pendurar propriedade num array

Como array é objeto, nada impede você de gravar uma chave não numérica nele. O motor aceita em silêncio, e o length finge que não viu:

js
const itens = ['Teclado mecânico', 'Mouse sem fio'];

itens.origem = 'importado';

console.log(itens.length);
console.log(itens);
console.log(Object.keys(itens));
2 [ 'Teclado mecânico', 'Mouse sem fio', origem: 'importado' ] [ '0', '1', 'origem' ]

length continua 2, mas Object.keys mostra três chaves. O Node até avisa imprimindo origem: 'importado' fora da contagem. Isso não é um recurso para usar: é uma explicação. Quando você precisar de nome e lista junto, use um objeto com um array dentro ({ origem: 'importado', itens: [...] }), não um array com propriedade grudada.

length é gravável, e isso corta ou estica o array

Na maioria das linguagens o tamanho da lista é leitura. Aqui, não:

js
const carrinho = ['Teclado mecânico', 'Mouse sem fio', 'Headset', 'Webcam'];

carrinho.length = 2;
console.log(carrinho);

carrinho.length = 4;
console.log(carrinho);
console.log(carrinho[3]);

carrinho.length = 0;
console.log(carrinho, carrinho.length);
[ 'Teclado mecânico', 'Mouse sem fio' ] [ 'Teclado mecânico', 'Mouse sem fio', <2 empty items> ] undefined [] 0

Diminuir length descarta os itens do fim, e não tem volta: aumentar de novo não traz 'Headset' de lugar nenhum, traz dois buracos. E length = 0 esvazia o array inteiro numa linha.

Esse truque do length = 0 aparece em código real porque ele esvazia o array no lugar, sem trocar a referência — quem mais aponta para aquele array vê o array vazio também. Se você fizer carrinho = [], cria um array novo e deixa o antigo intacto para os outros. São efeitos diferentes; escolha o que você quer.

Buraco não é undefined: o array esparso

Escrever num índice muito além do fim não dá erro. Cria vazio:

js
const estoque = [];

estoque[0] = 12;
estoque[4] = 3;

console.log(estoque);
console.log(estoque.length);
console.log(estoque[2]);
console.log(1 in estoque);
console.log(estoque.map((n) => n * 2));
[ 12, <3 empty items>, 3 ] 5 undefined false [ 24, <3 empty items>, 6 ]

Quatro coisas acontecem de uma vez. O length virou 5 sozinho. O Node imprime <3 empty items> em vez de undefined, undefined, undefined, porque essas posições não existem como chave. 1 in estoque é false — é assim que se distingue um buraco de uma posição que existe e vale undefined. E o map pulou os buracos: ele nem chamou a função para eles.

Índice fora do range devolve undefined, não erro

js
const carrinho = ['Teclado mecânico', 'Mouse sem fio', 'Headset'];

console.log(carrinho[3]);
console.log(carrinho[10]);
console.log(carrinho[-1]);
console.log(carrinho.at(-1));
undefined undefined undefined Headset

Nenhuma das três primeiras linhas quebrou. O motor procurou uma propriedade chamada '3', '10' e '-1', não achou e devolveu undefined — o mesmo que faria com carrinho.qualquerCoisa. Linguagens como Python levantam IndexError aqui; JavaScript, não.

Isso é a diferença entre falhar na hora e falhar depois. O programa segue carregando um undefined até o momento em que alguém tenta ler algo dentro dele. Aí, sim, ele para.

at(-1) é a exceção que confirma a regra: é um método, não uma leitura de chave, e conta a partir do fim.

O erro: Cannot read properties of undefined

Este é o erro número um de quem está aprendendo array. Um catálogo de três produtos e uma leitura na posição 10:

js
const produtos = [
  { nome: 'Teclado mecânico', preco: 289.9 },
  { nome: 'Mouse sem fio', preco: 149.9 },
  { nome: 'Headset', preco: 399 },
];

console.log(produtos[10].nome);
file:///private/tmp/loja/produtos.mjs:7 console.log(produtos[10].nome); ^ TypeError: Cannot read properties of undefined (reading 'nome') at file:///private/tmp/loja/produtos.mjs:7:26 at ModuleJob.run (node:internal/modules/esm/module_job:439:25) at async node:internal/modules/esm/loader:633:26 at async asyncRunEntryPointWithESMLoader (node:internal/modules/run_main:101:5) Node.js v24.16.0

Leia a mensagem de trás para a frente. reading 'nome' é o que você tentou ler; of undefined é o que estava no lugar do objeto. Ou seja: produtos[10] é que é undefined, não nome. O array não reclamou do índice 10 — ele entregou undefined e a linha seguinte tropeçou.

O caret aponta para a coluna 26, o n de nome — a primeira letra logo depois do ponto. Sempre que a seta cair depois de um ., o culpado é o que está à esquerda dele, nunca o nome que ela está apontando. Se esse erro é o seu companheiro diário, o guia do TypeError: Cannot read properties of undefined cobre os outros cenários em que ele aparece.

Três formas de não cair nele:

js
const produtos = [
  { nome: 'Teclado mecânico', preco: 289.9 },
  { nome: 'Mouse sem fio', preco: 149.9 },
  { nome: 'Headset', preco: 399 },
];

console.log(produtos[10]?.nome);
console.log(produtos.at(-1).nome);

const webcam = produtos.find((p) => p.nome === 'Webcam');
console.log(webcam?.preco ?? 'produto fora do catálogo');
undefined Headset produto fora do catálogo

O ?. (encadeamento opcional) devolve undefined em vez de quebrar. O ?? (coalescência nula) entrega um valor de reserva. E at(-1) resolve a necessidade mais comum — “o último” — sem você calcular índice nenhum.

Array de objetos: o formato de um carrinho de verdade

Na prática, array de string quase não aparece. O que aparece é array de objeto, porque cada linha do carrinho tem mais de uma informação:

js
const carrinho = [
  { nome: 'Teclado mecânico', preco: 289.9, quantidade: 1 },
  { nome: 'Mouse sem fio', preco: 149.9, quantidade: 2 },
];

const total = carrinho.reduce((soma, item) => soma + item.preco * item.quantidade, 0);

console.log(carrinho.length, 'itens');
console.log('R$', total.toFixed(2));
2 itens R$ 589.70

Repare que carrinho.length diz 2 linhas, não 3 peças. Quantidade é campo do item; tamanho é do array. Trocar um pelo outro é o motivo mais comum de o badge do carrinho mostrar um número e o checkout cobrar outro.

Cópia e referência

Array é um valor de referência: a variável guarda um endereço, não o conteúdo.

js
const original = ['Teclado mecânico', 'Mouse sem fio'];
const apelido = original;
const copia = [...original];

apelido.push('Headset');

console.log(original);
console.log(copia);
console.log(original === apelido, original === copia);
[ 'Teclado mecânico', 'Mouse sem fio', 'Headset' ] [ 'Teclado mecânico', 'Mouse sem fio' ] true false

apelido e original são dois nomes para o mesmo array — mexeu em um, mexeu no outro. copia é um array novo com os mesmos valores dentro. E === entre arrays compara o endereço, nunca o conteúdo: dois arrays com itens idênticos são sempre diferentes para o ===.

O que levar desta lição

Quatro frases que resolvem a maior parte dos bugs de array de iniciante:

  • O último índice é length - 1. Se você escreveu <= no laço, tem um undefined esperando.
  • Índice inválido não dá erro; dá undefined. O erro vem uma linha depois, quando alguém lê dentro desse undefined.
  • length é escrita, não só leitura — e length = 0 esvazia sem trocar a referência.
  • Array.isArray responde “isto é um array?”. typeof responde 'object' para array, objeto, null e data.

Teste o modelo do armário: crie const letras = ['A', 'B', 'C'], imprima letras[2], letras[3] e letras.at(-1), depois atribua letras[5] = 'F'. Confirme que o tamanho virou 6 e investigue as posições 3 e 4. Se você consegue explicar por que há buracos sem confundi-los com valores escritos como undefined, entendeu a parte mais importante da estrutura.

A próxima lição da trilha de JavaScript é adicionar e remover elementos de um array, onde push, splice e companhia mostram que const nunca prometeu proteger o conteúdo. Depois vem percorrer array em JavaScript. O guia completo de JavaScript mostra a ordem inteira.

  • arrays
  • indice
  • length
  • array esparso
  • estrutura de dados

Perguntas frequentes

Por que typeof de um array devolve "object"?
Porque array realmente é um objeto. Ele só tem um comportamento extra ligado às chaves numéricas e à propriedade length. typeof nunca vai distinguir os dois; para isso existe Array.isArray, que checa a marca interna do valor e funciona até entre iframes diferentes.
Array em JavaScript tem tamanho fixo?
Não. Ele cresce quando você escreve num índice maior que o atual e encolhe quando você diminui length. Isso é conveniente e também é armadilha: escrever em lista[500] num array de 3 itens não dá erro, só cria 497 buracos.
Posso guardar tipos diferentes no mesmo array?
Pode, o motor aceita. Na prática, evite. Um array com número, string e objeto misturados obriga quem percorre a testar o tipo item a item, e é onde nasce o TypeError que só aparece com o dado do cliente errado.
Qual a diferença entre lista[-1] e lista.at(-1)?
lista[-1] procura uma propriedade chamada "-1", que quase nunca existe, e devolve undefined. lista.at(-1) conta a partir do fim e devolve o último item. São coisas diferentes com aparência parecida.

Dúvidas e comentários

Travou em algum passo? Pergunte aqui — a equipe e outros alunos respondem.

Todo o código deste artigo foi executado em Node 24.16.0, e as saídas exibidas são as reais — como produzimos este conteúdo.

Fontes consultadas

  1. MDN — Indexed collections — developer.mozilla.org
  2. MDN — Array — developer.mozilla.org
  3. ECMAScript 2026 Language Specification — Array Exotic Objects — tc39.es

Continue por aqui