Referência de Coleções
Em C#, uma Referência de Coleções representa um conjunto estruturado de objetos que podem ser armazenados, manipulados e acessados de maneira eficiente. Coleções são fundamentais para o desenvolvimento de software, permitindo que programadores gerenciem dados de forma dinâmica, implementem algoritmos complexos e mantenham uma arquitetura orientada a objetos limpa e escalável. Elas são essenciais em aplicações de médio e grande porte, como sistemas financeiros, plataformas de e-commerce, sistemas de gerenciamento de usuários e aplicações em tempo real.
O uso de coleções em C# envolve conceitos centrais da linguagem, como generics, interfaces (IEnumerable, ICollection, IList), LINQ, além de princípios de OOP como encapsulamento e polimorfismo. Tipos comuns incluem List
Neste guia, você aprenderá como escolher a coleção adequada para cada tarefa, implementar algoritmos eficientes com essas estruturas, lidar com exceções, evitar vazamentos de memória e otimizar o desempenho do seu aplicativo. Também serão abordadas melhores práticas de desenvolvimento, integração com LINQ e técnicas avançadas de iteração, fornecendo um panorama completo para a construção de sistemas robustos e de alta performance em C#.
Exemplo Básico
textusing System;
using System.Collections.Generic;
namespace CollectionsReferenceExample
{
class Program
{
static void Main(string\[] args)
{
// Criação de uma lista de strings
List<string> frutas = new List<string> { "Maçã", "Banana", "Cereja" };
// Adicionando um novo elemento
frutas.Add("Laranja");
// Modificando um elemento existente
frutas[1] = "Manga";
// Iterando sobre os elementos
Console.WriteLine("Lista de frutas:");
foreach (string fruta in frutas)
{
Console.WriteLine(fruta);
}
// Verificando a existência de um elemento
if (frutas.Contains("Cereja"))
{
Console.WriteLine("Cereja está presente na lista.");
}
}
}
}
No exemplo acima, demonstramos o uso básico de List
Este padrão de uso é aplicável a cenários do mundo real, como manipulação de catálogos de produtos, listas de usuários ou dados temporários em memória. Ele ilustra conceitos de OOP, incluindo encapsulamento e modularidade, além de promover práticas seguras de gerenciamento de memória, pois a coleta de lixo (GC) do .NET gerencia os objetos da lista automaticamente. Entender essas operações básicas é essencial para construir aplicações escaláveis e eficientes.
Exemplo Prático
textusing System;
using System.Collections.Generic;
namespace AdvancedCollectionsExample
{
class Pessoa
{
public string Nome { get; set; }
public int Idade { get; set; }
}
class Program
{
static void Main(string[] args)
{
// Criação de um dicionário com identificadores únicos
Dictionary<int, Pessoa> pessoas = new Dictionary<int, Pessoa>();
pessoas.Add(1, new Pessoa { Nome = "Alice", Idade = 30 });
pessoas.Add(2, new Pessoa { Nome = "Bob", Idade = 25 });
pessoas.Add(3, new Pessoa { Nome = "Charlie", Idade = 35 });
// Acesso seguro a elementos
if (pessoas.TryGetValue(2, out Pessoa encontrado))
{
Console.WriteLine($"Pessoa encontrada: {encontrado.Nome}, {encontrado.Idade} anos");
}
// Iterando sobre o dicionário
foreach (var entry in pessoas)
{
Console.WriteLine($"ID: {entry.Key}, Nome: {entry.Value.Nome}");
}
// Removendo um elemento
pessoas.Remove(3);
}
}
}
Advanced C# Implementation
textusing System;
using System.Collections.Generic;
using System.Linq;
namespace EnterpriseCollectionsExample
{
class Produto
{
public string Nome { get; set; }
public decimal Preco { get; set; }
}
class Program
{
static void Main(string[] args)
{
try
{
// HashSet para elementos únicos
HashSet<Produto> produtos = new HashSet<Produto>(new ProdutoComparer())
{
new Produto { Nome = "Notebook", Preco = 1200 },
new Produto { Nome = "Tablet", Preco = 450 },
new Produto { Nome = "Notebook", Preco = 1200 } // duplicado ignorado
};
// LINQ para filtragem e ordenação
var produtosCaros = produtos
.Where(p => p.Preco > 500)
.OrderByDescending(p => p.Preco)
.ToList();
foreach (var p in produtosCaros)
{
Console.WriteLine($"Produto: {p.Nome}, Preço: {p.Preco}");
}
}
catch (Exception ex)
{
Console.WriteLine($"Erro: {ex.Message}");
}
}
}
class ProdutoComparer : IEqualityComparer<Produto>
{
public bool Equals(Produto x, Produto y)
{
return x.Nome == y.Nome && x.Preco == y.Preco;
}
public int GetHashCode(Produto obj)
{
return obj.Nome.GetHashCode() ^ obj.Preco.GetHashCode();
}
}
}
Estes exemplos avançados demonstram o uso de Dictionary\
Boas práticas em C# incluem utilizar coleções genéricas, selecionar a estrutura de dados correta conforme a necessidade, iterar com foreach para segurança, minimizar loops aninhados e tratar exceções de forma adequada. Evitar vazamentos de memória implica remover referências não utilizadas e testar performance com coleções grandes. Para aplicações multithreaded, recomenda-se usar coleções concorrentes. Otimizações podem incluir LINQ eficiente e Comparer personalizados. Considerações de segurança envolvem validação de dados antes de inserção e proteção de coleções compartilhadas entre threads.
📊 Referência Completa
C# Element/Method | Description | Syntax | Example | Notes |
---|---|---|---|---|
List<T> | Lista dinâmica ordenada | List<int> numeros = new List<int>(); | numeros.Add(10); | Acesso indexado, redimensionamento automático |
List<T>.Add() | Adiciona elemento | numeros.Add(10); | numeros.Add(5); | O(1) médio |
List<T>.Remove() | Remove elemento | numeros.Remove(10); | numeros.Remove(5); | Retorna true se removido |
List<T>.Contains() | Verifica existência | numeros.Contains(10); | bool existe = numeros.Contains(5); | Busca linear |
List<T>.Count | Quantidade de elementos | numeros.Count | int total = numeros.Count; | Atualiza dinamicamente |
Dictionary\<TKey,TValue> | Coleção chave-valor | Dictionary\<int,string> dict = new Dictionary\<int,string>(); | dict.Add(1,"Alice"); | Lookup rápido |
Dictionary\<TKey,TValue>.Add() | Adiciona par | dict.Add(1,"Alice"); | dict.Add(2,"Bob"); | Exceção se chave duplicada |
Dictionary\<TKey,TValue>.TryGetValue() | Acesso seguro | dict.TryGetValue(2,out string val); | bool achou = dict.TryGetValue(1,out string nome); | Evita exceção |
Dictionary\<TKey,TValue>.Remove() | Remove par | dict.Remove(1); | dict.Remove(2); | Retorna true se removido |
Dictionary\<TKey,TValue>.Keys | Chaves | var chaves = dict.Keys; | foreach(var key in dict.Keys) | Somente leitura |
Dictionary\<TKey,TValue>.Values | Valores | var valores = dict.Values; | foreach(var val in dict.Values) | Somente leitura |
Queue<T> | Fila FIFO | Queue<int> q = new Queue<int>(); | q.Enqueue(10); | First-In-First-Out |
Queue<T>.Enqueue() | Adiciona | q.Enqueue(10); | q.Enqueue(20) | O(1) |
Queue<T>.Dequeue() | Remove primeiro | q.Dequeue(); | int primeiro = q.Dequeue(); | Exceção se vazia |
Queue<T>.Peek() | Visualiza primeiro | q.Peek(); | int peek = q.Peek(); | Exceção se vazia |
Stack<T> | Pilha LIFO | Stack<int> s = new Stack<int>(); | s.Push(10); | Last-In-First-Out |
Stack<T>.Push() | Adiciona elemento | s.Push(10); | s.Push(20) | O(1) |
Stack<T>.Pop() | Remove topo | s.Pop(); | int topo = s.Pop(); | O(1), exceção se vazia |
Stack<T>.Peek() | Visualiza topo | s.Peek(); | int topo = s.Peek(); | Exceção se vazia |
HashSet<T> | Elementos únicos | HashSet<int> hs = new HashSet<int>(); | hs.Add(10); | Previne duplicatas |
HashSet<T>.Add() | Adiciona | hs.Add(10); | hs.Add(5); | False se já existe |
> .Remove() | Remove | hs.Remove(10); | hs.Remove(5); | Retorna true se removido |
> ObservableCollection<T> | Coleção observável | ObservableCollection<string> oc = new ObservableCollection<string>(); | oc.Add("Item"); | Notifica UI |
> ConcurrentDictionary\<TKey,TValue> | Thread-safe | ConcurrentDictionary\<int,string> cd = new ConcurrentDictionary\<int,string>(); | cd.TryAdd(1,"Alice"); | Multithread |
> ConcurrentQueue<T> | Thread-safe fila | ConcurrentQueue<int> cq = new ConcurrentQueue<int>(); | cq.TryDequeue(out int val); | Multithread |
> ConcurrentStack<T> | Thread-safe pilha | ConcurrentStack<int> cs = new ConcurrentStack<int>(); | cs.TryPop(out int val); | Multithread |
📊 Complete C# Properties Reference
Property | Values | Default | Description | C# Support |
---|---|---|---|---|
Count | int | 0 | Quantidade de elementos | Todas as coleções |
Capacity | int | dinâmica | Capacidade antes de expandir | List<T>, ArrayList |
IsReadOnly | bool | false | Indica se é somente leitura | ICollection<T>, IList<T> |
Keys | TKey Collection | N/A | Conjunto de todas as chaves | Dictionary\<TKey,TValue> |
Values | TValue Collection | N/A | Conjunto de todos os valores | Dictionary\<TKey,TValue> |
Comparer | IEqualityComparer | Default | Comparador para HashSet/Dictionary | HashSet<T>, Dictionary\<TKey,TValue> |
SyncRoot | object | null | Objeto para sincronização | ICollection |
IsSynchronized | bool | false | Indica thread-safety | ICollection |
CollectionChanged | Event | N/A | Evento de alteração | ObservableCollection<T> |
CapacityChanged | Event | N/A | Evento de alteração de capacidade | List<T> |
Comparer | IComparer | Default | Comparação em SortedList/SortedDictionary | SortedList\<TKey,TValue>, SortedDictionary\<TKey,TValue> |
O domínio das coleções em C# é crucial para qualquer desenvolvedor avançado. Compreender List
🧠 Teste Seu Conhecimento
Test Your Knowledge
Test your understanding of this topic with practical questions.
📝 Instruções
- Leia cada pergunta cuidadosamente
- Selecione a melhor resposta para cada pergunta
- Você pode refazer o quiz quantas vezes quiser
- Seu progresso será mostrado no topo