Apache Commons Collections Sac
1. introduction
Dans cet article rapide, nous allons nous concentrer sur l'utilisation de la collectionBag d'Apache.
Lectures complémentaires:
Apache Commons BeanUtils
Apprenez à utiliser Apache Commons BeanUtils pour des opérations courantes.
Apache Commons IO
Un guide rapide et pratique de la bibliothèque open source Apache Commons IO pour Java, qui couvre bon nombre de ses fonctionnalités les plus connues.
Introduction au texte Apache Commons
Apprenez à utiliser Apache Commons Text pour des opérations String courantes.
2. Dépendance Maven
Avant de commencer, nous devons importer les dernières dépendances deMaven Central:
org.apache.commons
commons-collections4
4.1
3. Sacs vs collections
En termes simples,Bag est une collection qui permet de stocker plusieurs éléments avec leur nombre de répétitions:
public void whenAdded_thenCountIsKept() {
Bag bag = new HashBag<>(
Arrays.asList(1, 2, 3, 3, 3, 1, 4));
assertThat(2, equalTo(bag.getCount(1)));
}
3.1. Violations du contratCollection
En lisant la documentation de l'API deBag, nous pouvons remarquer que certaines méthodes sont marquées comme ne respectant pas le contrat de collection Java standard.
Par exemple, lorsque nous utilisons une APIadd() d'une collection Java, nous recevonstrue même si l'élément est déjà dans la collection:
Collection collection = new ArrayList<>();
collection.add(1);
assertThat(collection.add(1), is(true));
La même API d'une implémentation deBag retournera unfalse lorsque nous ajoutons un élément qui est déjà disponible dans la collection:
Bag bag = new HashBag<>();
bag.add(1);
assertThat(bag.add(1), is(not(true)));
Pour résoudre ces problèmes, la bibliothèque d'Apache Collections fournit un décorateur appelé leCollectionBag.. Nous pouvons l'utiliser pour rendre nos collections de sacs conformes au contrat JavaCollection:
public void whenBagAddAPILikeCollectionAPI_thenTrue() {
Bag bag = CollectionBag.collectionBag(new HashBag<>());
bag.add(1);
assertThat(bag.add(1), is((true)));
}
4. Implémentations de sac
Explorons maintenant les différentes implémentations de l'interfaceBag - dans la bibliothèque de collections d'Apache.
4.1. HashBag
Nous pouvons ajouter un élément et indiquer à l'API le nombre de copies que cet élément devrait avoir dans notre collection de sacs:
public void givenAdd_whenCountOfElementsDefined_thenCountAreAdded() {
Bag bag = new HashBag<>();
bag.add(1, 5); // adding 1 five times
assertThat(5, equalTo(bag.getCount(1)));
}
Nous pouvons également supprimer un nombre spécifique de copies ou chaque instance d'un élément de notre sac:
public void givenMultipleCopies_whenRemove_allAreRemoved() {
Bag bag = new HashBag<>(
Arrays.asList(1, 2, 3, 3, 3, 1, 4));
bag.remove(3, 1); // remove one element, two still remain
assertThat(2, equalTo(bag.getCount(3)));
bag.remove(1); // remove all
assertThat(0, equalTo(bag.getCount(1)));
}
4.2. TreeBag
L'implémentation deTreeBag fonctionne comme n'importe quel autre arbre, en conservant en plus la sémantique deBag.
Nous pouvons naturellement trier un tableau d'entiers avec unTreeBag, puis interroger le nombre d'instances de chaque élément individuel dans la collection:
public void givenTree_whenDuplicateElementsAdded_thenSort() {
TreeBag bag = new TreeBag<>(Arrays.asList(7, 5,
1, 7, 2, 3, 3, 3, 1, 4, 7));
assertThat(bag.first(), equalTo(1));
assertThat(bag.getCount(bag.first()), equalTo(2));
assertThat(bag.last(), equalTo(7));
assertThat(bag.getCount(bag.last()), equalTo(3));
}
LeTreeBag implémente une interfaceSortedBag, toutes les implémentations de cette interface peuvent utiliser le décorateurCollectionSortedBag pour se conformer au contrat Java Collections:
public void whenTreeAddAPILikeCollectionAPI_thenTrue() {
SortedBag bag
= CollectionSortedBag.collectionSortedBag(new TreeBag<>());
bag.add(1);
assertThat(bag.add(1), is((true)));
}
4.3. SynchronizedSortedBag
Une autre implémentation largement utilisée deBag est leSynchronizedSortedBag. Précisément, il s'agit d'un décorateur synchronisé d'une implémentation deSortedBag.
Nous pouvons utiliser ce décorateur avec nosTreeBag (une implémentation deSortedBag) de la section précédente pour synchroniser l'accès à notre sac:
public void givenSortedBag_whenDuplicateElementsAdded_thenSort() {
SynchronizedSortedBag bag = SynchronizedSortedBag
.synchronizedSortedBag(new TreeBag<>(
Arrays.asList(7, 5, 1, 7, 2, 3, 3, 3, 1, 4, 7)));
assertThat(bag.first(), equalTo(1));
assertThat(bag.getCount(bag.first()), equalTo(2));
assertThat(bag.last(), equalTo(7));
assertThat(bag.getCount(bag.last()), equalTo(3));
}
Nous pouvons utiliser une combinaison d'API -Collections.synchronizedSortedMap() etTreeMap – pour simuler ce que nous avons fait ici avecSynchronizedSortedBag.
5. Conclusion
Dans ce court didacticiel, nous avons découvert l’interfaceBag et ses différentes implémentations.
Comme toujours, le code de cet article se trouveover on GitHub.