Nota
O acesso a esta página requer autorização. Pode tentar iniciar sessão ou alterar os diretórios.
O acesso a esta página requer autorização. Pode tentar alterar os diretórios.
Os termos a seguir são usados na ferramenta Memória , que é para investigar problemas de memória. Esses termos de memória são aplicáveis à análise de memória em geral, bem como a ferramentas de criação de perfil de memória para linguagens como Java ou .NET.
Para saber mais sobre como usar a ferramenta Memória, consulte Registrar instantâneos de heap usando a ferramenta Memória (tipo de criação de perfil "Heap snapshot")
O gráfico da memória
Pense na memória usada por uma página da Web como um gráfico: uma estrutura que contém nós conectados por bordas:
Os nós no gráfico de memória representam os objetos usados pela página, incluindo tipos primitivos, como números ou cadeias de caracteres JavaScript, e objetos, como matrizes associativas. Os nós e as arestas no gráfico de memória recebem os seguintes rótulos:
Os nós (ou objetos) são rotulados usando o nome da função construtora que foi usada para criá-los.
As arestas são rotuladas usando os nomes das propriedades.
Um nó no gráfico pode armazenar memória de duas maneiras:
Diretamente; A memória é mantida pelo próprio objeto.
Implicitamente, mantendo referências a outros objetos. Um objeto que contém referências a outros objetos impede que esses objetos sejam descartados automaticamente pela GC (coleta de lixo).
Heap JavaScript e memória de renderizador
O heap JavaScript é uma região de memória no processo do navegador em que todos os objetos JavaScript e WebAssembly residem. O heap JavaScript também é chamado de memória V8 (após o mecanismo JavaScript V8 que alimenta Microsoft Edge).
O heap JavaScript faz parte da memória do renderizador. A memória do renderizador é a memória usada pelo processo do navegador em que a página da Web é renderizada. A memória do renderizador é composta pelo seguinte:
- Memória nativa, como a memória usada por objetos C++ que representam os nós DOM.
- Memória heap JavaScript da página.
- Memória heap JavaScript de todos os trabalhos dedicados que são iniciados pela página.
A ferramenta Memória mostra:
- A memória V8.
- Os objetos alocados na memória nativa que são relevantes para a página da Web renderizada.
Raízes da coleta de lixo
As raízes da coleta de lixo (raízes GC) são criadas pelo navegador quando uma referência é feita do código nativo do navegador a um objeto JavaScript que está fora da máquina virtual V8. Essas referências são chamadas de alças.
Existem muitas raízes internas de GC, a maioria das quais não é interessante para desenvolvedores da Web. Do ponto de vista da página da Web, existem os seguintes tipos de raízes de GC:
Objetos globais da janela (um em cada iframe).
Às vezes, os objetos são retidos pelo contexto de depuração definido pelas ferramentas Fontes ou Console , como ao avaliar uma expressão JavaScript na ferramenta Console . Para remover esses objetos da ferramenta Memória, antes de gravar um snapshot de heap, limpe a ferramenta Console e desative os pontos de interrupção na ferramenta Fontes.
O gráfico de memória começa com uma raiz GC, que pode ser o window objeto do navegador ou o Global objeto de um módulo Node.js. Você não controla como o objeto raiz é coletado como lixo:
Os nós que não são acessíveis da raiz podem ser coletados como lixo.
Tamanhos e distâncias dos objetos
A ferramenta Memória exibe as seguintes colunas de informações:
- A coluna Distância
- A coluna de tamanho superficial
- A coluna Tamanho retido
Essas colunas são descritas abaixo.
Distância
A distância de um objeto no heap JavaScript é o número de nós no caminho mais curto entre o objeto e a raiz do GC. Quanto menor a distância, maior a probabilidade de esse objeto desempenhar um papel importante no uso da memória da página da Web.
Tamanho raso
O tamanho superficial é o tamanho do heap JavaScript que é mantido diretamente por um objeto. O tamanho superficial de um objeto geralmente é pequeno, porque um objeto JavaScript geralmente armazena apenas sua descrição do objeto, não os valores, na memória diretamente mantida do objeto. A maioria dos objetos JavaScript armazena seus valores em um repositório de backup que está em outro lugar no heap JavaScript e só expõe um pequeno objeto wrapper na parte do heap JavaScript que pertence diretamente ao objeto.
No entanto, mesmo um objeto pequeno pode conter uma grande quantidade de memória indiretamente, impedindo que outros objetos sejam descartados pelo processo de coleta de lixo.
Os números na coluna de tamanho superficial são o número de bytes.
Tamanho retido
O tamanho retido é o tamanho da memória que é implicitamente mantida por um objeto e que pode ser liberada depois que o objeto e outros responsáveis pela retenção existentes forem excluídos, juntamente com todos os objetos dependentes que se tornaram inacessíveis das raízes do GC.
Ou seja, o tamanho retido de um objeto é a quantidade de memória que seria recuperada se o objeto e todos os seus objetos dependentes fossem removidos do gráfico de memória.
O tamanho retido não pode ser menor do que o tamanho raso.
Quando um objeto é retido por vários nós, o tamanho do objeto aparece no tamanho retido do nó de retenção que tem o caminho mais curto para a raiz do GC.
Os números na coluna Tamanho retido são o número de bytes.
Retentores
Os responsáveis pela retenção de um objeto são os outros objetos que contêm referências ao objeto. A seção Retentores da ferramenta Memória mostra os objetos que contêm referências ao objeto selecionado na exibição Resumo .
A seção Retentores da ferramenta Memória é classificada por distância por padrão, o que significa que os caminhos de retenção mais simples para um objeto são mostrados primeiro.
Qualquer objeto sem retentores pode ser descartado pelo coletor de lixo do navegador, o que reduz o uso de memória.
Especificações do V8
Ao criar o perfil da memória, é útil entender por que os instantâneos de heap têm uma determinada aparência. Esta seção descreve como alguns objetos são armazenados na memória pela máquina virtual JavaScript V8 (abreviada aqui como VM V8 ou apenas VM), que pode ajudá-lo ao analisar instantâneos de heap na ferramenta Memória .
Primitivas de JavaScript
Em JavaScript, existem vários tipos primitivos, como:
- Números (como
3.14159). - Booleanos (
trueoufalse). - Cadeias de caracteres (como
"Werner Heisenberg").
Os primitivos não podem fazer referência a outros valores e são sempre nós folha (também chamados de nós de terminação) no gráfico de memória.
Os números podem ser armazenados como:
Valores inteiros imediatos de 31 bits chamados de SMIs (inteiros pequenos).
Objetos de heap, que são chamados de números de heap. Os números de heap são usados para armazenar valores que não se encaixam no formato de inteiro pequeno (SMI), como valores do tipo
double, ou quando um valor precisa ser encaixotado, como definir propriedades nele.
As cadeias de caracteres podem ser armazenadas em:
O heap de VM.
Externamente na memória do renderizador. Um objeto wrapper é criado e usado para acessar o armazenamento externo em que, por exemplo, as fontes de script e outros conteúdos recebidos da Web são armazenados, em vez de copiados no heap de VM.
Objetos JavaScript
A memória para novos objetos JavaScript é alocada a partir de um heap JavaScript dedicado (ou heap de VM). Esses objetos são gerenciados pelo coletor de lixo da VM V8 e, portanto, permanecem ativos enquanto houver pelo menos uma referência a eles.
Outros objetos
Objetos nativos: tudo o que não está armazenado no heap JavaScript é chamado de objeto nativo. Um objeto nativo, ao contrário de um objeto de heap, não é gerenciado pelo coletor de lixo V8 durante todo o seu tempo de vida e só pode ser acessado do JavaScript usando seu objeto wrapper JavaScript.
Cadeias de caracteres concatenadas: as cadeias de caracteres que são armazenadas e unidas, como resultado de uma concatenação de cadeia de caracteres em JavaScript, são armazenadas como cadeias de caracteres concatenadas no V8. A junção do conteúdo da cadeia de caracteres ocorre somente quando necessário, como quando uma subcadeia de caracteres de uma cadeia de caracteres unida precisa ser construída.
Por exemplo, se você concatenar
aeb, você obterá uma cadeia de caracteres(a, b)concatenada que representa o resultado da concatenação. Se você concatenarcposteriormente com esse resultado, receberá outra cadeia de caracteres concatenada:((a, b), c).Matrizes: uma matriz é um objeto que possui chaves numéricas. As matrizes são usadas extensivamente na VM V8 para armazenar grandes quantidades de dados. Conjuntos de pares chave-valor usados como dicionários são implementados como matrizes.
Um objeto JavaScript típico é armazenado como apenas um dos dois tipos de matriz:
- Uma matriz para armazenar propriedades nomeadas.
- Uma matriz para armazenar elementos numéricos.
Quando há um pequeno número de propriedades, as propriedades são armazenadas internamente no objeto JavaScript.
sistema / Mapa: um objeto que descreve tanto o tipo de objeto que é quanto o layout. Por exemplo, objetos de sistema/mapa são usados para descrever hierarquias de objetos implícitos para acesso rápido à propriedade. Consulte Propriedades rápidas na V8.
Observação
Partes desta página são modificações baseadas no trabalho criado e compartilhado pelo Google e usadas de acordo com os termos descritos na Licença Creative Commons Atribuição 4.0 Internacional. A página original é encontrada aqui e é de autoria de Meggin Kearney.
Este trabalho está licenciado sob uma Licença Creative Commons Atribuição 4.0 Internacional.