Resumo : neste tutorial, você aprenderá sobre valores e tipos de referência C# e como o .NET armazena os objetos do tipo de valor e referência na memória.
Gerenciamento de memória
Quando um programa C# é executado, ele armazena dados na memória. Normalmente, um programa em execução usa duas regiões principais na memória para armazenar dados:
- A pilha
- A pilha
A pilha
A pilha é uma matriz de memória que funciona com base no princípio LIFO (último a entrar, primeiro a sair). A pilha permite adicionar ou remover dados do topo dela:
A pilha tem duas operações principais, push e pop:
- Colocar os dados no topo da pilha é chamado de push.
- A remoção de dados do topo da pilha é chamada de popping.
A imagem a seguir ilustra uma pilha:
A pilha armazena o seguinte tipo de dados:
- Valores de alguns tipos de variáveis.
- Parâmetros passados para métodos.
- O ambiente de execução atual do programa.
A pilha
O heap é uma área de memória onde você pode armazenar um determinado tipo de dados. Ao contrário da pilha, os dados na pilha podem ser adicionados ou removidos em qualquer ordem.
A imagem a seguir ilustra a memória heap:
Normalmente, um programa pode armazenar itens no heap, mas não pode excluí-los explicitamente. Em vez disso, o coletor de lixo (GC) limpa automaticamente os objetos heap órfãos quando determina que o programa não precisa mais deles.
A imagem a seguir mostra que o programa não faz mais referência a um dado no heap:
O GC começará a recuperá-lo:
E após a coleta de lixo, a memória é liberada para reutilização:
Valor C# e tipos de referência
C# divide os tipos em duas categorias:
- Tipos de valor
- Tipos de referência
E C# armazena os objetos de tipos de valor e tipos de referência de maneira diferente.
Os tipos de valor requerem apenas um único local de memória que armazena os dados reais. C# armazena objetos de tipos de valor na pilha:
Exemplos de tipos de valor são byte, short, short, int, long, bool, struct e enum.
Os tipos de referência requerem dois locais na memória:
- O primeiro contém os dados reais que sempre estão localizados na pilha.
- A segunda é uma referência que aponta para os dados reais. C# armazena a referência na pilha.
A imagem a seguir ilustra como C# armazena um objeto de um tipo de referência:
Exemplos de tipos de referência são string , object e tipos definidos pelo usuário, incluindo class , interface , delegado e array .
Armazenando membros de um objeto de um tipo de referência
C# sempre armazena os dados reais de um objeto de um tipo de referência no heap. Isso significa que se o objeto tiver membros que são tipos de valor, o C# também armazena os dados desses membros no heap.
A imagem a seguir ilustra como C# armazena o membro de um objeto de um tipo de referência:
Verificando se um tipo é um valor ou tipo de referência
Para verificar se o tipo é um valor ou tipo de referência, você usa o typeof
operador para obter a System.Type
instância de um tipo e verificar a IsValueType
propriedade.
Se a IsValueType
propriedade retornar verdadeiro, o tipo será um tipo de valor. Caso contrário, é um tipo de referência.
O seguinte ilustra o uso da propriedade typeof
and IsValueType
para verificar se int
e string
são tipos de valor ou referência:
using static System.Console;
WriteLine(typeof(int).IsValueType); // True
WriteLine(typeof(string).IsValueType); // False
Linguagem de código: C# ( cs )
Saída:
True
False
Linguagem de código: C# ( cs )
Resumo
- Um programa em execução usa duas regiões principais da memória: a pilha e o heap.
- O coletor de lixo remove automaticamente os objetos do heap quando o programa não os utiliza mais.
- C# armazena dados de tipos de valor na pilha e dados de tipos de referência no heap.