Java 21 na Prática: Records, Pattern Matching, Virtual Threads e o Futuro do Desenvolvimento Java

Por que o Java 21 é um Marco na Linguagem?
O Java 21, lançado em setembro de 2023 como uma versão LTS (Long-Term Support), representa o ápice de anos de inovação contínua no ecossistema Java. Diferente de versões anteriores que traziam mudanças incrementais, o Java 21 entrega um conjunto de funcionalidades que redefine a experiência de desenvolvimento: desde a sintaxe mais concisa com Records e Pattern Matching até a revolução na concorrência com Virtual Threads.
Neste artigo, você vai aprender na prática cada um desses recursos com exemplos de código que podem ser aplicados imediatamente no seu dia a dia.
Records: Dados Imutáveis com Menos Código
Introduzidos como preview no Java 14 e tornados estáveis no Java 16, os Records eliminam a cerimônia de criar classes de dados. Com uma única linha, você declara uma classe imutável com construtor, getters, equals(), hashCode() e toString() automaticamente gerados pelo compilador.
// Antes do Java 16 - dezenas de linhas de boilerplate
public class Pessoa {
private final String nome;
private final int idade;
public Pessoa(String nome, int idade) {
this.nome = nome;
this.idade = idade;
}
public String nome() { return nome; }
public int idade() { return idade; }
@Override
public boolean equals(Object o) { /* implementacao manual */ }
@Override
public int hashCode() { /* implementacao manual */ }
@Override
public String toString() { /* implementacao manual */ }
}
// Com Records (Java 16+) - uma linha!
public record Pessoa(String nome, int idade) {}Records sao ideais para DTOs, value objects, respostas de API e qualquer estrutura que represente dados imutaveis. No Java 21, Records podem ser combinados com Pattern Matching para criar codigo ainda mais expressivo.
Pattern Matching para instanceof
Pattern Matching elimina a necessidade do classico padrao "verifique o tipo, faca cast, use a variavel". Agora voce faz tudo em um unico passo:
// Antes do Java 16
if (obj instanceof String) {
String s = (String) obj;
System.out.println(s.length());
}
// Com Pattern Matching (Java 16+)
if (obj instanceof String s) {
System.out.println(s.length()); // s ja esta no escopo!
}No Java 21, o Pattern Matching foi estendido para funcionar com switch expressions, permitindo padroes complexos com guards:
public String processar(Object obj) {
return switch (obj) {
case null -> "Valor nulo";
case String s && s.length() > 10 -> "String longa: " + s;
case String s -> "String curta: " + s;
case Integer i && i < 0 -> "Numero negativo: " + i;
case Integer i -> "Numero positivo: " + i;
case Record r -> "Record: " + r.toString();
default -> "Tipo desconhecido";
};
}
Virtual Threads: Concorrencia Leve e Escalavel
Virtual Threads (Project Loom) e, sem duvida, o recurso mais impactante do Java 21. Eles permitem criar milhoes de threads leves que sao gerenciadas pela JVM, nao pelo sistema operacional. Isso resolve o gargalo historico de aplicacoes Java com alta concorrencia.
// Thread tradicional - cara e limitada pelo SO
Thread plataforma = new Thread(() -> {
System.out.println("Thread de plataforma (OS)");
});
// Virtual Thread (Java 21) - leve, milhoes possiveis
Thread virtual = Thread.startVirtualThread(() -> {
System.out.println("Virtual Thread (JVM)");
});
// Com ExecutorService
try (var executor = Executors.newVirtualThreadPerTaskExecutor()) {
IntStream.range(0, 100_000).forEach(i -> {
executor.submit(() -> {
Thread.sleep(1000); // Nao bloqueia a thread OS!
return i;
});
});
} // Virtual threads sao gerenciadas como pilhas na heapO segredo das Virtual Threads e que elas nao bloqueiam threads do sistema operacional durante operacoes de I/O. Quando uma virtual thread encontra um bloqueio (como Thread.sleep() ou uma chamada de rede), ela e "montada" - sua pilha e movida para a heap - e a thread OS fica livre para executar outras virtual threads.
Isso significa que voce pode escrever codigo sincrono tradicional (sem callbacks, sem reactive streams) e ainda assim obter a escalabilidade de um modelo assincrono. Frameworks como Spring Boot 3.2+ e Quarkus ja oferecem suporte nativo a Virtual Threads.
Sequenced Collections: Ordem Previsivel
O Java 21 introduziu SequencedCollection, SequencedSet e SequencedMap - novas interfaces que padronizam operacoes em colecoes com ordem definida:
SequencedCollection<String> lista = new ArrayList<>();
lista.add("Primeiro");
lista.add("Segundo");
lista.add("Terceiro");
String primeiro = lista.getFirst(); // "Primeiro"
String ultimo = lista.getLast(); // "Terceiro"
lista.addFirst("Novo Primeiro"); // Adiciona no inicio
lista.addLast("Novo Ultimo"); // Adiciona no fim
SequencedCollection<String> reverso = lista.reversed();Antes do Java 21, cada implementacao (ArrayList, LinkedList, TreeSet) tinha suas proprias formas nao padronizadas de acessar primeiro e ultimo elementos. Agora o contrato e unificado.
String Templates (Preview)
String Templates, em preview no Java 21, trazem interpolacao segura de strings diretamente na linguagem:
String nome = "Maria";
int idade = 28;
// Template processor - FMT para formatacao
String mensagem = STR."Ola, \{nome}! Voce tem \{idade} anos.";
// Com expressoes
int a = 5, b = 3;
String resultado = STR."\{a} + \{b} = \{a + b}"; // "5 + 3 = 8"
// FMT formata numeros
String preco = FMT."Preco: %.2f\{19.99}"; // "Preco: 19,99"Diferente da concatenacao tradicional com + ou String.format(), String Templates sao verificados em tempo de compilacao e oferecem seguranca contra injecao de codigo quando usados com template processors especificos como SQL.
Melhorias em switch e Pattern Matching
O Java 21 tornou estaveis as switch expressions com pattern matching e record patterns, permitindo desestruturar Records diretamente:
record Endereco(String rua, int numero) {}
record Cliente(String nome, Endereco endereco) {}
public void exibirDados(Object obj) {
switch (obj) {
case Cliente(String nome, Endereco(var rua, var num)) ->
System.out.printf("%s mora na %s, %d%n", nome, rua, num);
case null -> System.out.println("Sem dados");
default -> System.out.println(obj);
};
}Essa sintaxe permite navegar por estruturas de dados aninhadas com clareza e seguranca - eliminando completamente a necessidade de casts e null checks manuais.
Conclusao e Proximos Passos
O Java 21 nao e apenas mais uma versao - e uma reinvencao da experiencia de programar em Java. Com Records, Pattern Matching e Virtual Threads, a linguagem se torna mais concisa, segura e escalavel sem abrir mao da compatibilidade com versoes anteriores que sempre foi sua marca registrada.
Para comecar a usar esses recursos hoje:
- Atualize seu JDK para a versao 21 LTS - disponivel na Oracle, OpenJDK, Amazon Corretto e Adoptium
- Atualize suas dependencias - Spring Boot 3.2+, Quarkus 3.6+ e Hibernate 6.3+ ja suportam Java 21
- Refatore gradualmente - comeca substituindo classes de dados por Records e depois explore Virtual Threads em servicos com alta concorrencia de I/O
- Habilite preview features - String Templates e outras funcionalidades em preview podem transformar ainda mais seu codigo
O futuro do Java ja chegou - e esta mais produtivo do que nunca.







