Feature Java: Sequenced Collections
O Java 21 lançou a feature Sequenced Collections para simplificar ainda mais o uso de coleções. Esse aprimoramento da linguagem auxilia o desenvolvedor no momento em que é necessário realizar alguma operação nos primeiros ou últimos registros de uma coleção.
Este post visa explorar a nova funcionalidade, demonstrando sua aplicação em diversos tipos de coleções por meio de exemplos.
Sequenced Collections Interfaces
Essa nova funcionalidade introduziu três novas interfaces:
SequencedCollection
A interface SequencedCollection
estende Collection
e declara os seguintes métodos:
-
SequencedCollection<E> reversed(): Retorna uma visão ordenada inversa da coleção.
-
void addFirst(E e): Adiciona um elemento como o primeiro elemento da coleção.
-
void addLast(E e): Adiciona um elemento como o último elemento da coleção.
-
E getFirst(): Retorna o primeiro elemento da coleção.
-
E getLast(): Retorna o último elemento da coleção.
-
E removeFirst(): Remove e retorna o primeiro elemento da coleção.
-
E removeLast(): Remove e retorna o último elemento da coleção.
SequencedSet
Já a interface SequencedSet
estende SequencedCollection
declara apenas um único método:
-
SequencedSet<E> reversed(): Retorna uma visão ordenada inversa da coleção.
SequencedMap
A interface SequencedMap
estende Map
e declara os seguintes métodos:
-
SequencedMap<K, V> reversed(): Retorna uma visão ordenada inversa do mapa.
-
Map.Entry<K,V> firstEntry(): Retorna o primeiro mapeamento do mapa.
-
Map.Entry<K,V> lastEntry(): Retorna o último mapeamento do mapa.
-
Map.Entry<K,V> pollFirstEntry(): Remove e retorna o primeiro mapeamento do mapa.
-
Map.Entry<K,V> pollLastEntry(): Remove e retorna o último mapeamento do mapa.
-
V putFirst(K k, V v): Insere como o primeiro registro do mapa se ainda não estiver presente.
-
V putLast(K k, V v): Insere como o último registro do mapa se ainda não estiver presente.
-
SequencedSet<K> sequencedKeySet(): Retorna um SequencedSet contendo as chaves do mapa.
-
SequencedCollection<V> sequencedValues(): Retorna uma SequencedCollection contendo os valores do mapa.
-
SequencedSet<Map.Entry<K, V>>: Retorna um SequencedSet contendo o mapeamento do mapa.
Exemplos
Neste primeiro exemplo utilizaremos os métodos providos pela interface SequencedCollection
.
public static void main(String[] args) {
var nomes = new ArrayList<String>();
nomes.add("Gaspar");
nomes.add("Laura");
System.out.println(nomes.getFirst()); // Gaspar
nomes.addFirst("Cecilia");
nomes.addLast("Murilo");
System.out.println(nomes.getFirst()); // Cecilia
System.out.println(nomes.getLast()); // Murilo
var nomesReverso = nomes.reversed();
System.out.println(nomesReverso.getFirst()); // Murilo
System.out.println(nomesReverso.getLast()); // Cecilia
System.out.println(nomesReverso.removeFirst()); // Murilo
System.out.println(nomesReverso.removeFirst()); // Laura
System.out.println(nomesReverso.removeLast()); // Cecilia
}
Exemplo de utilização do SequencedSet
num conjunto de frutas, acessando todos os métodos disponibilizados pela interface.
public static void main(String[] args) {
var frutas = new LinkedHashSet<>();
frutas.add("Banana");
frutas.add("Maça");
System.out.println(frutas.getFirst()); // Banana
frutas.addFirst("Abacate");
frutas.addLast("Melancia");
System.out.println(frutas.getFirst()); // Abacate
System.out.println(frutas.getLast()); // Melancia
var frutasReverso = frutas.reversed();
System.out.println(frutasReverso.getFirst()); // Melancia
System.out.println(frutasReverso.getLast()); // Abacate
System.out.println(frutasReverso.removeFirst()); // Melancia
System.out.println(frutasReverso.removeFirst()); // Maça
System.out.println(frutasReverso.removeLast()); // Abacate
}
Em nosso último exemplo, utilizaremos todos os novos métodos providos pela interface SequencedMap
.
public static void main(String[] args) {
var mapa = new LinkedHashMap<String, String>();
mapa.put("chave-gaspar", "Gaspar Barancelli");
mapa.put("chave-laura", "Laura Barancelli");
System.out.println(mapa.firstEntry().getValue()); // Gaspar Barancelli
mapa.putFirst("chave-cecilia", "Cecilia Barancelli");
mapa.putLast("chave-murilo", "Murilo Barancelli");
System.out.println(mapa.firstEntry().getValue()); // Cecilia Barancelli
System.out.println(mapa.lastEntry().getValue()); // Murilo Barancelli
var values = mapa.sequencedValues();
System.out.println(values.getFirst()); // Cecilia Barancelli
System.out.println(values.getLast()); // Murilo Barancelli
var chaves = mapa.sequencedKeySet();
System.out.println(chaves.getFirst()); // chave-cecilia
System.out.println(chaves.getLast()); // chave-murilo
var mapeamento = mapa.sequencedEntrySet();
System.out.println(mapeamento.getFirst().getValue()); // Cecilia Barancelli
System.out.println(mapeamento.getLast().getValue()); // Murilo Barancelli
var mapaReverso = mapa.reversed();
System.out.println(mapaReverso.firstEntry().getValue()); // Murilo Barancelli
System.out.println(mapaReverso.lastEntry().getValue()); // Cecilia Barancelli
System.out.println(mapaReverso.pollFirstEntry().getValue()); // Murilo Barancelli
System.out.println(mapaReverso.pollFirstEntry().getValue()); // Laura Barancelli
System.out.println(mapaReverso.pollLastEntry().getValue()); // Cecilia Barancelli
}
Conclusão
As Sequenced Collections do Java 21 representam um salto significativo na forma como gerenciamos coleções, especialmente quando o foco está nos primeiros ou últimos elementos. As novas interfaces e métodos introduzidos facilitam o acesso, a manipulação e a visualização de dados de maneira intuitiva e eficiente.