Collection = plusieurs choses regroupées, dont le regroupement peut être manipulé comme un tout.
Les collections définissent 2 structures de base :
- Une
Collection est un regroupement d'objets.
- Une
Map est un groupement d'associations (= dictionnaire, tableau associatif).
- Set : traduit la notion mathématique d'ensemble ; ne peut pas contenir de doublons (notamment un seul élément
null) ; les éléments ne sont pas ordonnés (mais le sont dans unOrderedSet). - List : collection ordonnée.
- Queue : collection ordonnée fournissant des méthodes supplémentaires pour extraire les éléments par ordre d'arrivée (souvent FIFO, parfois LIFO).
- Deque : "double ended queue" ; les éléments peuvent être récupérés aux deux extrémités de la queue.
- Map : dictionnaire, ou tableau associatif permettant de gérer des associations clé - valeur.
Lorsqu'on choisit une implémentation de Collection pour travailler, prendre en compte les performances, suivant les cas d'utilisation.
Par ex,
LinkedList a de très bonnes preformances pour l'ajout / suppression d'éléments, mais pas pour du random access.
Voir la marker interface
java.util.RandomAccess :
List<?> l = ...; if(!(l instanceof RandomAccess)) l = new ArrayList<?>(l);
ArrayList est une implémentation très souvent utilsée.
Vector n'est là que pour des raisons de compatibilité ascendante, utiliser ArrayList à la place.
Stack n'est là que pour des raisons de compatibilité ascendante, utiliser Deque à la place.
Deux classes contenant des utilitaires (méthodes statiques) souvent utilisés :
-
java.util.Collections
-
java.util.Arrays
Voir aussi
java.lang.System.arraycopy(), java.lang.Class.isArray()
L'interface collection
Définit les méthodes communes à toutes les implémentations, voir l'apidoc dejava.util.Collection.
Collection<E>, paramétrée par le type d'éléments qu'elle contient.
Quelques exemples d'utilisation :
// création "normale"
Collection<String> c1 = new ArrayList<>();
// création à partir de méthodes utilitaires
Collection<String> c2 = Arrays.asList("toto", "titi");
// La plupart des implémentations ont un constructeur par recopie
Collection<String> c3 = new ArrayList<String>(c2);
// Ajout
c2.add("tata"); // Ajout d'un élément
c3.addAll(c2); // Ajout de tous les éléments d'une autre collection
// Suppression
c2.remove("toto"); // Supprime un seul élément
c2.removeAll(c3); // Supprime une collection d'élément
c2.retainAll(c3); // Supprime tous les éléments qui ne sont pas dans c3
c.clear(); // RAZ, supprime tous les éléments d'une collection
// Accès aux éléments
c2.get(1);
// Taille d'une collection
boolean b = c1.isEmpty(); // c is now empty, so true
int s = c1.size();
// La plupart des implementations de Collection ont redéfini toString()
System.out.println(c1);
// Conversion vers un tableau.
Object[] elements = c.toArray();
String[] strings = c.toArray(new String[c.size()]);
(code dans Demo1.java)
Toutes ces opérations sont utilisables avec n'importe quelle implémentation des sous-interfaces de Collection (Set, List ou Queue).
Itération
Itération classique
Boucle for ou foreach :
List<String> c = new ArrayList<String>();
for(String word : c) {
System.out.println(word);
}
for( declaration : expression )
statement
Iterator
expression doit être un tableau, ou une classe implémentant java.lang.Iterable.
public interface Iterable<E> {
java.util.Iterator<E> iterator();
}
Dans une boucle classique, l'itérateur sous-jacent est invisible.
on peut explicitement utiliser l'itérateur d'une collection car
java.util.Collection définit une méthode :
public Iterator<E> iterator()Une boucle classique équivaut à :
List<String> c = new ArrayList<String>();
for(Iterator<String> i = c.iterator(); i.hasNext();) {
System.out.println(i.next());
}
Utilisable aussi avec while :
Iterator<String> iterator() = c.iterator();
while (iterator.hasNext()) {
System.out.println(iterator.next());
}
Interface java.util.Iterator :
public interface Iterator<E> {
boolean hasNext();
E next();
void remove();
}
Attention, next() fait 2 choses : renvoie l'élément courant de l'itération ET avance dans la collection.
Iterator est paramétré par le type de la collection qu'elle traverse :
Il faut un
Iterator<String> pour parcourir une Collection<String>.
Maps
Une map est une collection contenant des associations clé, valeur ; parfois appelé dictionnaire ou tableau associatif.Exemples d'utilisation :
import java.util.*;
class Personne{
private String nom;
public Personne(String nom) { this.nom = nom; }
@Override public String toString() { return nom; }
}
public class MapTest{
public static void main(String[] args) {
// création de la map
Map<String, Personne> map = new HashMap<>();
map.put("p1", new Personne("Personne 1"));
map.put("p2", new Personne("Personne 2"));
map.put("p3", new Personne("Personne 3"));
// Affichage
System.out.println("=== Utilisation de values() ===");
for(Personne p : map.values()) {
System.out.println(p); // n'affiche que les valeurs
}
System.out.println("=== Utilisation de keySet() ===");
for(String key : map.keySet()) {
System.out.println(key + " : " + map.get(key));
}
System.out.println("=== Utilisation de entrySet() ===");
for(Map.Entry<String, Personne> entry : map.entrySet()) {
System.out.println(entry.getKey() + " : " + entry.getValue());
}
System.out.println("=== Utilisation de iterator() ===");
Iterator<Map.Entry<String, Personne>> entries = map.entrySet().iterator();
while(entries.hasNext()) {
Map.Entry<String, Personne> entry = entries.next();
System.out.println(entry.getKey() + " : " + entry.getValue());
}
System.out.println("=== Utilisation de stream() ===");
map.forEach((k,v)->System.out.println(k + " : " + v));
}
}