Pular para o conteúdo
.NETGenerics (`<T>`)
Módulo 01Fundamentos da Plataforma e da Linguagem

Generics (`<T>`)

intermediario 28 min de leitura·Atualizado · .NET 9
Resumo

Generics permitem escrever classes e métodos que funcionam com qualquer tipo, sem perder segurança de tipos nem cair em boxing. São a base de List<T>, Task<T>, repositórios genéricos e muito mais.

1. Objetivos de Aprendizagem#

  • Criar classes e métodos genéricos.
  • Aplicar restrições (where) a parâmetros de tipo.
  • Entender por que generics evitam boxing e casts.

2. Pré-requisitos#

  • Interfaces (tópico 5.3).

3. Conceito#

Um parâmetro de tipo (T) é um "espaço reservado" preenchido quando você usa a classe/método. O porquê: escrever a lógica uma vez e reutilizá-la com segurança de tipos para qualquer T, sem object (que traria boxing e casts).

Restrições (where) limitam o que T pode ser:

  • where T : class / struct — referência / valor.
  • where T : new() — deve ter construtor sem parâmetros.
  • where T : IEntidade — deve implementar uma interface.

4. Mão na Massa#

4.1. Setup#

Shell
dotnet new console -n Catalog.Generics
cd Catalog.Generics

4.2. Implementação Passo a Passo#

  1. Método genérico:
C#
T PrimeiroOuPadrao<T>(IEnumerable<T> itens, T padrao)
{
    foreach (var item in itens) return item;
    return padrao;
}

Console.WriteLine(PrimeiroOuPadrao(new[] { 3, 4 }, 0)); // 3
  1. Classe genérica com restrição:
C#
public interface IEntidade { Guid Id { get; } }

public class Repositorio<T> where T : IEntidade
{
    private readonly List<T> _itens = new();
    public void Adicionar(T item) => _itens.Add(item);
    public T? PorId(Guid id) => _itens.FirstOrDefault(x => x.Id == id);
}
  1. Uso:
C#
public record Produto(Guid Id, string Nome) : IEntidade;

var repo = new Repositorio<Produto>();
repo.Adicionar(new Produto(Guid.NewGuid(), "Mouse"));

4.3. Executando#

Shell
dotnet run

5. Exemplo Completo#

Repositorio<T> funciona para qualquer entidade que tenha Id, com segurança de tipos total — nenhum cast, nenhum boxing. É o embrião do repositório genérico usado em APIs.

6. Boas Práticas e Armadilhas#

FaçaEvite
Usar restrições where para exigir capacidades de TCair em object e casts manuais
Nomear parâmetros de tipo claramente (T, TKey, TEntity)Generics excessivamente abstratos e ilegíveis
Nota

generics em .NET preservam o tipo em runtime (diferente do "type erasure" de outras plataformas), o que permite reflexão e evita boxing de value types.

7. Segurança e Produção#

  • Código genérico bem restrito reduz duplicação — menos lugares para introduzir bugs e mais fácil de manter.

8. Exercícios#

  • Fácil: escreva um método genérico Trocar<T>(ref T a, ref T b).
  • Médio: adicione uma restrição where T : IEntidade a uma classe.
  • Desafio: implemente um Cache<TKey, TValue> genérico simples com Dictionary.

9. Resumo#

Generics reutilizam lógica para qualquer tipo com segurança e sem boxing; where impõe restrições. São a base de coleções e repositórios do .NET.

10. Próximos Passos#

A seguir, as interfaces que unificam coleções: IEnumerable e afins.

11. Referências#

07-02 — Generics (`<T>`) | Curso ASP.NET Core