Objetos: agrupar dados relacionados.
Criação literal, acesso por ponto e colchete, optional chaining. Desestruturação, spread e imutabilidade. Referência vs. valor.
Objetos agrupam dados relacionados em uma única estrutura. Um artigo tem título, autor, data, tags, curtidas — em vez de manter cinco variáveis separadas, você mantém um objeto artigo com cinco propriedades. É a estrutura de dados fundamental para modelar entidades do mundo real.
Criar e acessar propriedades
A forma mais direta de criar um objeto é o literal de objeto — chaves delimitadas por {}, com pares de chave: valor separados por vírgulas:
const artigo = {
id: 1,
titulo: "Meu primeiro projeto web",
slug: "meu-primeiro-projeto-web",
autor: "Dev Aprendiz",
publicadoEm: "2025-03-15",
curtidas: 42,
tags: ["html", "css", "javascript"],
publicado: true,
}; Property shorthand: quando o valor de uma propriedade é uma variável com o mesmo nome da chave, você pode omitir o valor — { titulo } é equivalente a { titulo: titulo }:
const titulo = "CSS em geral";
const autor = "Dev Aprendiz";
const curtidas = 87;
// shorthand: { titulo } = { titulo: titulo }
const artigo = { titulo, autor, curtidas }; O acesso por ponto (artigo.titulo) funciona para chaves que são identificadores válidos — sem espaços, sem caracteres especiais, não começando com número. O acesso por colchete (artigo["titulo"]) funciona para qualquer chave, incluindo chaves dinâmicas (variáveis) e chaves com caracteres especiais:
// ponto: chave estática e simples
artigo.titulo // → "CSS em geral"
artigo.curtidas // → 87
// colchete: chave dinâmica (variável)
const propriedade = "titulo";
artigo[propriedade] // → "CSS em geral"
// colchete: chave com caractere especial
const dados = { "publicado-em": "2025-03-15" };
dados["publicado-em"] // → "2025-03-15"
// dados.publicado-em // SyntaxError — hífen não é válido em identificador Optional chaining (?.) protege o acesso a propriedades de objetos possivelmente null ou undefined. Em vez de lançar um erro, retorna undefined:
const artigo = {
titulo: "CSS em geral",
autor: { nome: "Dev Aprendiz", bio: null },
};
// sem optional chaining — pode lançar TypeError
// artigo.autor.redesSociais.twitter // TypeError se redesSociais for undefined
// com optional chaining — retorna undefined sem erro
artigo.autor?.redesSociais?.twitter // → undefined
// também funciona com chamadas de método
artigo.autor?.formatarNome?.() // → undefined se formatarNome não existir
// e com acesso por colchete
artigo?.["titulo"] // → "CSS em geral" Desestruturação
Desestruturação extrai propriedades de um objeto em variáveis com o mesmo nome:
const artigo = {
id: 1,
titulo: "CSS em geral",
autor: "Dev Aprendiz",
curtidas: 87,
publicadoEm: "2025-03-15",
};
// desestruturação básica
const { titulo, autor, curtidas } = artigo;
console.log(titulo); // → "CSS em geral"
console.log(curtidas); // → 87
// renomear durante a desestruturação
const { titulo: tituloDoArtigo, autor: nomeDoAutor } = artigo;
// valor padrão — usado se a propriedade for undefined
const { curtidas: totalCurtidas = 0, destaque = false } = artigo;
// destaque → false (não existe no artigo, usa padrão)
// desestruturação aninhada
const artigo2 = {
titulo: "Flexbox",
metadados: { tempo: 7, nivel: "intermediário" },
};
const { metadados: { tempo, nivel } } = artigo2;
console.log(tempo); // → 7
console.log(nivel); // → "intermediário" Spread e imutabilidade
O operador spread ... copia as propriedades de um objeto para um novo. As propriedades listadas depois sobrescrevem as copiadas:
const artigo = { id: 1, titulo: "CSS em geral", curtidas: 87 };
// adicionar curtida sem mutar o original
const artigoAtualizado = { ...artigo, curtidas: artigo.curtidas + 1 };
// artigo → { id: 1, titulo: "CSS em geral", curtidas: 87 }
// artigoAtualizado → { id: 1, titulo: "CSS em geral", curtidas: 88 }
// sobrescrever uma propriedade
const artigoDestacado = { ...artigo, destaque: true };
// merge de dois objetos — as chaves do segundo sobrescrevem o primeiro
const padroes = { tema: "claro", idioma: "pt-BR", animacoes: true };
const preferencias = { tema: "escuro" }; // usuário mudou apenas o tema
const configuracao = { ...padroes, ...preferencias };
// → { tema: "escuro", idioma: "pt-BR", animacoes: true } O spread é uma cópia rasa (shallow copy): propriedades de primeiro nível são copiadas por valor, mas objetos aninhados ainda compartilham referência:
const original = {
titulo: "CSS em geral",
autor: { nome: "Dev Aprendiz" }, // objeto aninhado
};
const copia = { ...original };
// propriedade de primeiro nível — copiada por valor
copia.titulo = "Outro título";
console.log(original.titulo); // → "CSS em geral" (não afetado)
// objeto aninhado — compartilha referência
copia.autor.nome = "Outro Autor";
console.log(original.autor.nome); // → "Outro Autor" (afetado!) Iterar sobre objetos
Objetos não são iteráveis diretamente com for...of. Use os métodos de Object:
const estatisticas = {
visualizacoes: 1240,
curtidas: 87,
comentarios: 23,
compartilhamentos: 45,
};
// apenas as chaves
Object.keys(estatisticas);
// → ["visualizacoes", "curtidas", "comentarios", "compartilhamentos"]
// apenas os valores
Object.values(estatisticas);
// → [1240, 87, 23, 45]
// pares [chave, valor] — o mais útil para iterar
Object.entries(estatisticas);
// → [["visualizacoes", 1240], ["curtidas", 87], ...]
// iterar e renderizar cada estatística
for (const [chave, valor] of Object.entries(estatisticas)) {
console.log(`${chave}: ${valor}`);
}
// ou converter para array e usar map
const labels = Object.entries(estatisticas).map(([chave, valor]) => `${chave}: ${valor}`); Referência vs. valor
Tipos primitivos (string, number, boolean, null, undefined) são copiados por valor — cada variável tem sua própria cópia.
Objetos e arrays são copiados por referência — a variável guarda o endereço de memória do objeto, não o objeto em si. Quando você faz const b = a, b e a apontam para o mesmo objeto:
// primitivos: cópia por valor
let x = 42;
let y = x;
y = 100;
console.log(x); // → 42 (não afetado)
// objetos: cópia por referência
const artigo = { titulo: "CSS em geral", curtidas: 87 };
const referencia = artigo; // não é uma cópia — é outro nome para o mesmo objeto
referencia.curtidas = 100;
console.log(artigo.curtidas); // → 100 (afetado!)
// para verificar igualdade, === compara referências
const a = { x: 1 };
const b = { x: 1 };
a === b // → false (objetos diferentes na memória, mesmo conteúdo)
const c = a;
a === c // → true (mesma referência)
// para criar uma cópia real (rasa), use spread
const copia = { ...artigo };
copia.curtidas = 0;
console.log(artigo.curtidas); // → 100 (spread criou um objeto separado) Resumo
- Literal de objeto
{ chave: valor }é a forma padrão de criação. Property shorthand{ titulo }omite o valor quando é igual à chave. - Ponto para chaves estáticas e simples; colchete para chaves dinâmicas ou com caracteres especiais.
- Optional chaining
?.retornaundefinedem vez de lançar erro em objetos possivelmente nulos — essencial para dados que podem estar incompletos. - Desestruturação
const { titulo, autor = "Anônimo" } = artigoextrai propriedades em variáveis. Suporta renomeação e valores padrão. - Spread
{ ...objeto, novaProp: valor }cria um novo objeto com as propriedades do original. Cópia rasa — objetos aninhados ainda compartilham referência. - Objetos e arrays são copiados por referência —
const b = anão cria uma cópia. Use spread para criar objetos independentes.
Qual é a diferença entre acesso por ponto (artigo.titulo) e por colchete (artigo['titulo'])?
O que o optional chaining (?.) faz?
Por que objetos e arrays em JavaScript são copiados por referência?
O que é property shorthand em um objeto literal?
Aula concluída
Quase lá.