Documentação de C#
Referência concisa e baseada em exemplos de C#. Leia o conceito, veja o código e pratique em uma jornada da Coddy.
Inicie uma jornada guiada de C#Primeiros passos
- O que é C#C# é uma linguagem de uso geral e tipagem estática da Microsoft que roda no .NET. Para que ela serve, como se relaciona com o .NET, o que cada versão adicionou e como um programa em C# é montado.
- Hello WorldSeu primeiro programa em C# linha por linha: o método Main, Console.WriteLine e Write, ler a entrada com Console.ReadLine, comentários, criar e executar um projeto com a CLI do dotnet e instruções de nível superior.
- C# vs JavaC# e Java se parecem e resolvem problemas parecidos. As diferenças reais estão em propriedades, tipos de valor, genéricos, LINQ versus streams, async, exceções e nos ecossistemas em volta. Uma comparação lado a lado com código.
- C# vs C++C# é uma linguagem gerenciada com garbage collector; C++ compila para código nativo e dá controle manual sobre a memória. Como essa diferença aparece em segurança, desempenho, motores de jogos, modelo de build e na dificuldade de aprender cada uma.
- Namespaces e usingComo os namespaces organizam os tipos em C# e como a diretiva using os importa: aliases, using static, nomes totalmente qualificados, como resolver referências ambíguas, global usings e namespaces com escopo de arquivo.
Fundamentos
- VariáveisComo declarar e atribuir variáveis em C#, quando var é uma boa ideia e quando não é, como funciona o escopo, a diferença entre const, readonly e static readonly, as convenções de nomes e o erro de variável não atribuída.
- Tipos de dadosTodos os tipos embutidos de C# com tamanho, intervalo e sufixo de literal, a diferença entre tipos de valor e de referência, por que decimal é o tipo para dinheiro, overflow de inteiros e checked, e valores padrão.
- String para intComo converter uma string para int em C# com int.Parse, int.TryParse e Convert.ToInt32, como funcionam os casts implícitos e explícitos, por que o cast de um double trunca, os operadores as e is, e por que "1.5" pode virar 15.
- OperadoresOs operadores de C# com o comportamento exato: divisão inteira, o operador de resto com números negativos, incremento e atribuição composta, comparação, lógica com curto-circuito, operadores bit a bit, os operadores de null e uma tabela de precedência.
- StringsComo as strings funcionam em C#: imutabilidade, Length e índices, comparar com ==, Equals e string.Compare, caracteres de escape, strings verbatim com @ e texto multilinha, raw string literals, verificações de null e vazio e percorrer caracteres.
- SubstringComo String.Substring funciona em C#: os argumentos de índice inicial e tamanho, a ArgumentOutOfRangeException e como evitá-la, extrair texto em volta de resultados do IndexOf, pegar os primeiros ou os últimos n caracteres e o operador de intervalo do C# 8.
- Interpolação de stringsComo funciona a interpolação de strings com $"..." em C#: expressões entre chaves, especificadores de formato como F2, N0, C, D5 e X, alinhamento para tabelas, escape de chaves, string.Format e formatação composta, strings interpoladas verbatim e raw, e formatação para uma cultura específica.
- Métodos de stringOs métodos de String que você usa todo dia em C#: Split com vários separadores e opções, Replace, Contains e busca sem diferenciar maiúsculas e minúsculas, IndexOf e LastIndexOf, StartsWith e EndsWith, Trim, ToUpper e ToLower, PadLeft, Join, Concat e inverter uma string.
- StringBuilderPor que concatenar strings repetidamente em um laço é lento em C#, e como o StringBuilder resolve isso: Append, AppendLine, AppendFormat, Insert, Remove, Replace, capacidade, e quando a concatenação simples ou string.Join é a melhor escolha.
- Números aleatóriosComo gerar números aleatórios em C# com a classe Random: Next e o limite superior exclusivo, doubles aleatórios em um intervalo, sementes para resultados reproduzíveis, sortear um elemento, embaralhar uma lista, a armadilha do new Random dentro de um laço e números criptograficamente seguros.
- DateTimeTrabalhando com datas e horas em C#: criar valores DateTime, Now vs UtcNow vs Today, somar dias e meses, subtrair para obter um TimeSpan, TotalHours vs Hours, comparar datas, DayOfWeek, converter com ParseExact e TryParse, DateTimeOffset e DateOnly.
- Formato de DateTimeComo formatar um DateTime como string em C#: as strings de formato padrão (d, D, o, s, u, t), padrões personalizados como yyyy-MM-dd HH:mm:ss, uma tabela completa de especificadores, como a cultura muda a saída, ISO 8601 de ida e volta com "o" e os erros de mm vs MM e hh vs HH.
Controle de fluxo
- if elseComo if, else if e else funcionam em C#: por que as condições precisam ser bool, como combinar testes com &&, || e !, quando as chaves importam, guard clauses no lugar de aninhamento profundo, e os bugs de = versus == e do ponto e vírgula perdido.
- switch caseComo a instrução switch funciona em C#: switch com valores int, string, char e enum, por que todo case precisa de break (erro CS0163), empilhar rótulos case para vários valores, goto case, default, diferença entre maiúsculas e minúsculas em strings e rótulos case com padrões e when.
- Expressão switchA expressão switch do C# 8 transforma um valor em um resultado com braços de padrão, sem case e break. Sintaxe, o descarte _, padrões de propriedade, de tupla e relacionais, and/or/not, guardas when, avisos de exaustividade e SwitchExpressionException, com equivalentes executáveis em C# 7.
- Operador ternárioO operador condicional de C# condition ? a : b escolhe um de dois valores. Como ele é avaliado, por que os dois ramos precisam de um tipo comum (CS0173) e o cast que resolve, ternários aninhados, parênteses na interpolação de strings e quando ?? e ?. dizem isso melhor.
- Laço forComo o laço for funciona em C#: inicializador, condição e iterador, contagem regressiva e passos, várias variáveis de controle, percorrer arrays por índice, laços aninhados, for(;;), e os bugs de off by one e de remover itens durante a iteração.
- Laço foreachComo o foreach funciona em C#: percorrer arrays, listas, strings e dicionários (KeyValuePair e desconstrução), obter o índice, por que a variável do laço é somente leitura, a InvalidOperationException "Collection was modified" e como resolvê-la, e o que um tipo precisa ter para ser usado no foreach.
- Laço whileComo os laços while e do while funcionam em C#: a condição verificada antes ou depois do corpo, ler a entrada até um valor sentinela ou até o fim, while (true) com break, e os erros de laço infinito que pegam muita gente.
- break e continueComo break, continue e goto funcionam em C#: encerrar um laço antes do fim, pular uma iteração, break dentro de um switch, três formas de sair de laços aninhados (uma flag, goto ou um método com return) e o bug do laço infinito com continue dentro de um while.
Métodos e delegates
- MétodosComo declarar e chamar métodos em C#: tipos de retorno e void, parâmetros, métodos com corpo de expressão, retornar vários valores com uma tupla, sobrecarga, arrays params, métodos static versus de instância, o método Main, recursão e funções locais.
- Parâmetros opcionaisComo parâmetros opcionais e argumentos nomeados funcionam em C#: valores padrão e a regra da constante de tempo de compilação, ordem dos parâmetros, pular argumentos pelo nome, parâmetros opcionais versus sobrecargas, atributos de informação do chamador e a armadilha de versionamento dos padrões gravados em quem chama.
- ref e outComo os parâmetros ref, out e in funcionam em C#: passar a variável em vez de uma cópia, out para resultados extras e o padrão TryParse, out var, parâmetros in somente leitura, as regras de atribuição definida e o que muda quando o argumento é um tipo de referência.
- Expressões lambdaComo as expressões lambda funcionam em C#: a sintaxe => em todas as formas, guardar lambdas em Func e Action, passá-las para métodos e para o LINQ, lambdas de instrução, closures sobre variáveis capturadas e o bug de captura no laço for que o foreach não tem.
- DelegatesO que é um delegate em C# e como usá-lo: declarar um tipo delegate, criá-lo a partir de um método, uma lambda ou um método anônimo, invocá-lo, delegates como callbacks, delegates multicast com += e -=, verificação de null com ?.Invoke e como os delegates se relacionam com Func, Action e eventos.
- Func e ActionComo Func e Action funcionam em C#: Func<T, TResult> para funções que retornam um valor, Action<T> para as que não retornam, Predicate e Comparison, passar e retornar funções, um dicionário de comandos, lambdas async e quando declarar o seu próprio delegate.
- EventosComo os eventos funcionam em C#: declarar um evento com EventHandler e EventHandler<T>, classes EventArgs próprias, inscrever e cancelar a inscrição com += e -=, disparar um evento com segurança usando ?.Invoke, por que um evento é melhor que um campo delegate público e o vazamento de memória causado por uma inscrição esquecida.
- Métodos de extensãoComo os métodos de extensão funcionam em C#: um método static em uma classe static com this no primeiro parâmetro, chamado como se fosse um método de instância, estendendo string, enums e IEnumerable<T>, como o LINQ é construído com eles, por que métodos de instância vencem, receptores null e a diretiva using de que eles precisam.
Coleções e LINQ
- ArraysUm array em C# é um bloco de tamanho fixo com elementos de um só tipo. Veja como declarar e inicializar arrays, ler o Length, ordenar e buscar com a classe Array, copiá-los com segurança e trabalhar com arrays 2D e jagged.
- ListList<T> é o array que cresce do C#. Veja como criar uma lista, adicionar e inserir itens, remover por valor, índice ou condição, buscar com Contains e Find, ordenar por uma propriedade e evitar o erro de modificar uma lista dentro de um foreach.
- DictionaryDictionary<TKey, TValue> mapeia chaves para valores com busca rápida. Veja como adicionar e atualizar entradas, ler com segurança usando TryGetValue, percorrer entradas KeyValuePair, contar ocorrências, ignorar maiúsculas e minúsculas nas chaves e manter as chaves ordenadas com SortedDictionary.
- HashSetHashSet<T> guarda itens únicos e responde ao Contains em tempo constante. Veja como o Add informa duplicatas, como remover duplicados de uma lista, como fazer união, interseção e diferença de conjuntos e como fazer um conjunto comparar seus próprios objetos pelo valor.
- Queue (fila)Queue<T> é uma coleção em que o primeiro a entrar é o primeiro a sair: os itens saem na ordem em que chegaram. Veja Enqueue, Dequeue e Peek, a exceção da fila vazia e o TryDequeue, busca em largura com uma fila e quando usar ConcurrentQueue ou PriorityQueue.
- Stack (pilha)Stack<T> é uma coleção em que o último a entrar é o primeiro a sair: o item adicionado mais recentemente sai primeiro. Veja Push, Pop e Peek, a exceção da pilha vazia e o TryPop, por que uma pilha é enumerada ao contrário e dois usos clássicos: um histórico de desfazer e a verificação de parênteses balanceados.
- TuplasUma tupla em C# agrupa alguns valores em um só sem declarar um tipo. Veja a sintaxe de value tuple, elementos nomeados, retornar vários valores de um método, desconstruir com var (a, b), tuplas como chave de dicionário e como ValueTuple difere do antigo System.Tuple.
- LINQO LINQ adiciona operadores de consulta a toda coleção em C#. Veja a sintaxe de métodos e a sintaxe de consulta, filtrar com Where, projetar com Select, ordenar com OrderBy e ThenBy, agrupar com GroupBy, a armadilha de First vs FirstOrDefault, agregações e como a execução adiada muda o momento em que a consulta executa.
- IEnumerable e yieldIEnumerable<T> é a interface por trás do foreach e do LINQ, e yield return é a forma mais fácil de implementá-la. Veja como IEnumerable se relaciona com ICollection e List, como um método iterador executa passo a passo, yield break, sequências infinitas e as armadilhas da avaliação preguiçosa.
Classes e tipos
- Classes e objetosComo declarar uma classe em C#, dar a ela campos e métodos, criar objetos com new e o que significa uma classe ser um tipo de referência: objetos compartilhados, null e NullReferenceException, ToString e inicializadores de objeto.
- ConstrutoresComo os construtores funcionam em C#: o construtor padrão implícito e quando ele desaparece, construtores com parâmetros e sobrecarregados, encadeamento com this(...) e base(...), a ordem em que tudo executa, construtores static e private, e os construtores primários do C# 12.
- PropriedadesComo as propriedades funcionam em C#: acessores get e set sobre um campo de apoio, auto-properties, private set e propriedades só com get, propriedades calculadas, validação nos setters e as palavras-chave init e required do C# 9 e 11.
- Palavra-chave staticO que static significa em C#: membros que pertencem ao tipo em vez de a um objeto, estado compartilhado entre instâncias, métodos static e classes static, construtores static, const vs static readonly, using static e o erro CS0120.
- Modificadores de acessoOs seis modificadores de acesso de C# (public, private, protected, internal, protected internal, private protected), o que cada um permite, os padrões quando você não escreve nenhum e os erros de compilação que eles produzem.
- HerançaComo a herança de classes funciona em C#: derivar com dois pontos, o que é e o que não é herdado, chamar a classe base com base, virtual e override, ocultar com new (e a saída que surpreende todo mundo), sealed, polimorfismo e casts para cima e para baixo na hierarquia.
- Classes abstratasO que é uma classe abstrata em C#: uma classe base que não pode ser instanciada e pode declarar membros abstratos que as classes derivadas precisam implementar. Cobre métodos e propriedades abstratos, construtores, o padrão template method e quando escolher uma interface.
- InterfacesComo as interfaces funcionam em C#: declarar uma, implementá-la em classes e structs, usar a interface como tipo, implementar várias ao mesmo tempo, implementação explícita, as interfaces do framework que você mais vai implementar (IComparable<T>, IEnumerable<T>, IDisposable) e os métodos padrão de interface do C# 8.
- StructsComo as structs funcionam em C#: semântica de valor e cópia na atribuição, o erro de modificação em List<T>, regras dos construtores, igualdade, boxing, readonly struct e record struct, e uma comparação entre struct e class com orientações sobre quando uma struct é a escolha certa.
- EnumsComo os enums funcionam em C#: declarar constantes com nome, valores inteiros subjacentes e cast, converter um enum para string e uma string para enum com Parse e TryParse, listar todos os valores, [Flags] com operadores bit a bit e HasFlag, switch sobre um enum e tratamento de valores indefinidos.
- RecordsO que são os records em C# (C# 9 em diante): sintaxe posicional, os membros que o compilador gera, igualdade baseada em valor, cópias não destrutivas com with, o ToString embutido, record struct do C# 10, herança entre records e a classe equivalente escrita à mão.
- GenéricosComo os genéricos funcionam em C#: escrever classes e métodos genéricos com parâmetros de tipo, inferência de tipos, restrições com where (class, struct, new(), classes base, interfaces), default(T), membros static por tipo e covariância com IEnumerable<out T>.
- Tipos anuláveisTudo sobre null em C#: tipos de valor anuláveis (int?, Nullable<T>) com HasValue, Value e GetValueOrDefault, os operadores de coalescência nula ?? e ??=, o operador condicional nulo ?., verificações de null e os tipos de referência anuláveis (string?) do C# 8.
- Pattern matchingComo o pattern matching funciona em C#: o operador is com padrões de tipo e de constante, instruções switch com padrões nos case e when, expressões switch, padrões de propriedade, de tupla e posicionais, padrões relacionais e lógicos (and, or, not), padrões de lista e em que versão de C# cada um chegou.
Exceções
- try catchtry, catch e finally são a forma como C# trata exceções. Veja como uma exceção sobe pela pilha de chamadas, como capturar tipos específicos de exceção na ordem certa, filtrar com when, fazer a limpeza no finally, relançar com throw; sem perder o stack trace e quais exceções não capturar.
- Lançar exceçõesComo e quando lançar exceções em C#. Veja a instrução throw, qual tipo de exceção embutido combina com cada erro, throw expressions com ?? e ?:, os auxiliares ThrowIfNull e como escrever uma classe de exceção própria com seus dados e uma inner exception.
- Instrução usingA instrução using garante que o Dispose seja chamado em arquivos, streams, conexões e outros objetos IDisposable, mesmo quando uma exceção é lançada. Veja para o que ela é compilada, a ordem em que os objetos são descartados, a declaração using do C# 8 e como implementar IDisposable na sua própria classe.
Assincronia e threads
- async awaitasync e await permitem que código C# espere operações lentas sem bloquear uma thread. Veja como um método async executa, Task e Task<T>, executar operações independentes ao mesmo tempo com Task.WhenAll, exceções em código async e por que async void e .Result causam bugs e deadlocks.
- TasksTask é a unidade de trabalho assíncrono e paralelo no .NET. Veja Task.Run para trabalho limitado pela CPU, ler resultados, combinar tasks com WhenAll e WhenAny, continuações, cancelar com CancellationToken, como uma Task difere de uma Thread e quando Parallel.For é a melhor escolha.
- Instrução lockA instrução lock permite que só uma thread por vez execute um bloco de código. Veja uma condição de corrida corromper um contador, corrija-a com lock, saiba em qual objeto fazer o lock, use Interlocked para contadores simples, evite deadlocks causados pela ordem dos locks e use SemaphoreSlim quando o código dentro dele faz await.
- TimerC# tem várias classes de timer, e elas se comportam de forma diferente. Veja quando usar System.Threading.Timer, System.Timers.Timer, PeriodicTimer ou um timer de interface, como iniciá-los e pará-los, por que os callbacks executam no thread pool e podem se sobrepor, por que um timer precisa continuar referenciado e como medir o tempo decorrido com Stopwatch.
Arquivos, JSON e mais
- Ler e escrever arquivosComo escrever em um arquivo e ler um arquivo em C#: File.WriteAllText, ReadAllText, AppendAllText, WriteAllLines e ReadAllLines para arquivos inteiros, StreamWriter e StreamReader para os grandes, caminhos com Path.Combine, diretórios, codificações e as exceções que o código de arquivos precisa tratar.
- JSONComo trabalhar com JSON em C# usando System.Text.Json: JsonSerializer.Serialize e Deserialize, saída em camelCase e indentada, atributos como JsonPropertyName e JsonIgnore, enums como strings, ler JSON sem classes com JsonDocument e JsonNode, erros e a comparação com o Newtonsoft.Json.
- RegexComo usar expressões regulares em C# com System.Text.RegularExpressions: IsMatch, Match e Matches, grupos numerados e nomeados, Replace com substituições e com uma lambda, Split, RegexOptions, strings verbatim para padrões, validar entradas, timeouts e o atributo GeneratedRegex do .NET 7.
- Reflection e atributosComo funciona a reflection em C#: objetos Type a partir de typeof e GetType, ler e definir propriedades, chamar métodos pelo nome, criar instâncias, e os atributos: os embutidos como Obsolete, declarar os seus e lê-los em tempo de execução. Mais o que a reflection custa.