Immutabilité des chaînes et pool de chaînes
Comprenez pourquoi les chaînes sont immuables, comment fonctionne le pool de chaînes et quand utiliser == plutôt que equals.
Immutabilité des chaînes et pool de chaînes est une leçon Java Academy gratuite sur CoddyKit. Ceci est la leçon 1 sur 4. Tu peux lire la leçon complète ci-dessous gratuitement — puis la pratiquer en direct dans le navigateur avec un éditeur de code intégré et un tuteur IA 24/7. Elle fait partie du parcours d'apprentissage Java Academy, et ta progression se synchronise sur le web et l'application CoddyKit. Le cours Java Academy comprend 4 leçons au total.
Immutabilité de String et pool de String
Les chaînes sont immuables dans Java. Comprendre l'immutabilité, le pool de String et la différence entre égalité des références et égalité des valeurs permet d'éviter des bogues subtils.
Pourquoi les String sont immuables
Les objets String ne peuvent pas être modifiés après leur création. Toute opération qui « modifie » une String crée en réalité un nouvel objet String. Cela permet le partage, la sécurité vis-à-vis des threads et la mise en cache de hashCode.
String s = "hello";
s.toUpperCase(); // creates a new String, does NOT modify s
System.out.println(s); // still "hello"
String upper = s.toUpperCase(); // must capture the result
System.out.println(upper); // HELLOLe pool de String (mise en pool)
Les littéraux String sont stockés dans le pool de String (une zone spéciale du tas). Deux littéraux ayant le même contenu partagent le même objet.
String a = "hello"; // goes into pool
String b = "hello"; // same object from pool
String c = new String("hello"); // forces new object outside pool
System.out.println(a == b); // true (same pool reference)
System.out.println(a == c); // false (different objects)
System.out.println(a.equals(c)); // true (same content)== contre equals()
Utilisez toujours .equals() pour comparer le contenu d'une String. L'opérateur == vérifie si deux variables pointent vers le même objet (égalité des références).
String input = new String("admin"); // from user input, not pooled
String role = "admin";
// Dangerous: fails because different objects
if (input == role) System.out.println("Same"); // not printed!
// Correct: compares content
if (input.equals(role)) System.out.println("Equal!"); // prints
// Null-safe: put constant first to avoid NPE
if ("admin".equals(input)) System.out.println("Admin"); // printsintern() : mise en pool manuelle d'une String
String.intern() force une String à entrer dans le pool et renvoie la référence mise en pool. Cette opération est rarement nécessaire dans les versions modernes de Java.
String s1 = new String("interned");
String s2 = s1.intern();
String s3 = "interned"; // already in pool
System.out.println(s2 == s3); // true (both point to pool)
System.out.println(s1 == s3); // false (s1 is off-pool)
// Modern use: prefer String.intern() only when you need
// identity-based caching with thousands of repeated stringsComportement de la concaténation de String
La concaténation avec + crée de nouveaux objets String. Dans une boucle, sa complexité est en O(n²). Le compilateur optimise les expressions uniques, mais pas la concaténation effectuée dans une boucle.
// Compiler optimizes this to a StringBuilder automatically:
String result = "Hello, " + "World" + "!";
// In loops: compiler does NOT optimize — use StringBuilder explicitly!
List<String> words = List.of("a", "b", "c", "d");
String bad = ""; // O(n^2) — new object each iteration
for (String w : words) bad += w;
StringBuilder sb = new StringBuilder();
for (String w : words) sb.append(w); // O(n) — efficient
String good = sb.toString();
System.out.println(good); // abcdComparer correctement les String
Utilisez toujours equals() ; pour une comparaison insensible à la casse, utilisez equalsIgnoreCase(). Utilisez compareTo() pour l'ordre lexicographique.
String a = "Java";
String b = "java";
System.out.println(a.equals(b)); // false
System.out.println(a.equalsIgnoreCase(b)); // true
System.out.println(a.compareToIgnoreCase(b)); // 0 (equal)
System.out.println(a.compareTo(b)); // negative (J < j in Unicode)Mise en cache du hashCode de String
Comme les chaînes sont immuables, Java met hashCode en cache après le premier appel. Les appels suivants renvoient la valeur mise en cache, ce qui rend les chaînes très efficaces comme clés de HashMap.
String key = "product:12345";
// hashCode computed once and cached:
int h1 = key.hashCode();
int h2 = key.hashCode(); // returns cached value
System.out.println(h1 == h2); // true
// Strings are ideal HashMap keys because:
// 1. hashCode is consistent (immutable content)
// 2. hashCode is cached (fast repeated lookups)
// 3. equals is well-defined (content-based)
Map<String, Integer> map = new HashMap<>();
map.put("key", 42);
System.out.println(map.get("key")); // 42String est finale
La classe String est final : elle ne peut pas être étendue. Cela garantit qu'aucune sous-classe ne peut compromettre l'immutabilité ou la cohérence de hashCode.
// String is final — this will not compile:
// class MutableString extends String {} // compile error
// You cannot override String behavior.
// If you need custom string-like behavior, use a wrapper:
record ProductSku(String value) {
ProductSku { if (!value.matches("[A-Z]{3}-[0-9]{4}")) throw new IllegalArgumentException(); }
@Override public String toString() { return value; }
}String.format contre concaténation
Pour les chaînes composées de plusieurs parties, préférez String.format() ou les blocs de texte à la concaténation, afin d'améliorer la lisibilité et de faciliter la localisation.
String name = "Alice";
int age = 30;
double score = 97.5;
// Concatenation — harder to read with many parts
String bad = "User: " + name + ", Age: " + age + ", Score: " + score;
// String.format — clear placeholders
String good = String.format("User: %s, Age: %d, Score: %.1f", name, age, score);
System.out.println(good);
// User: Alice, Age: 30, Score: 97.5Opérations sur String sans risque de null
De nombreuses opérations sur String lèvent NPE si la chaîne est nulle. Utilisez des schémas défensifs ou String.valueOf() pour gérer les valeurs nulles en toute sécurité.
String value = null;
// Null-safe length check
int len = (value != null) ? value.length() : 0;
System.out.println(len); // 0
// Null-safe comparison (put constant first)
boolean isAdmin = "admin".equals(value); // false, no NPE
// String.valueOf converts null to "null" string
System.out.println(String.valueOf(value)); // "null"
System.out.println(Objects.toString(value, "default")); // "default"Vérification rapide
Que produit le code suivant ?
String a = "hello";
String b = new String("hello");
System.out.println(a.equals(b));
System.out.println(a == b);Récapitulatif : immutabilité de String et pool de String
Points essentiels :
- Les chaînes sont immuables : les opérations renvoient de nouveaux objets String et ne modifient jamais l'original
- Les littéraux String sont mis en pool : deux littéraux ayant le même contenu partagent un seul objet
- Utilisez toujours .equals() pour comparer le contenu d'une String ; == compare les références des objets
- Utilisez equalsIgnoreCase() pour les comparaisons insensibles à la casse
- La concaténation de chaînes dans les boucles est en O(n²) : utilisez StringBuilder pour gagner en efficacité
- Les chaînes mettent hashCode en cache, ce qui les rend efficaces et sûres comme clés de HashMap
Questions Fréquemment Posées
La leçon « Immutabilité des chaînes et pool de chaînes » est-elle gratuite ?
Oui — le texte complet de « Immutabilité des chaînes et pool de chaînes » est gratuit à lire ici sur le web. Pour la pratiquer de manière interactive (un éditeur de code intégré et un tuteur IA 24/7) et déverrouiller le reste du cours Java Academy, passe à CoddyKit PRO. Le cours Java Academy comprend 4 leçons au total.
Qu'est-ce que j'apprendrai dans « Immutabilité des chaînes et pool de chaînes » ?
Comprenez pourquoi les chaînes sont immuables, comment fonctionne le pool de chaînes et quand utiliser == plutôt que equals. Tu pratiques Java Academy avec du code pratique que tu exécutes directement dans le navigateur, et un tuteur IA 24/7 répond à tes questions au fur et à mesure que tu avances dans la leçon.
Dois-je avoir de l'expérience pour commencer Java Academy ?
Aucune expérience préalable n'est requise. Java Academy sur CoddyKit est structuré pour les débutants jusqu'aux apprenants avancés, donc tu peux commencer ici ou depuis le début et avancer à ton rythme. Ceci est la leçon 1 sur 4.
Combien de temps prend la leçon « Immutabilité des chaînes et pool de chaînes » ?
La plupart des leçons CoddyKit prennent environ 5–10 minutes. Chacune est courte et interactive, tu progresses régulièrement et tu repiques exactement où tu t'es arrêté sur le web et l'app.
Peux-tu écrire et exécuter du code dans cette leçon Java Academy ?
Oui. Chaque leçon Java Academy inclut un éditeur de code intégré, tu écris et exécutes du vrai code directement dans ton navigateur et tu reçois des retours IA instantanés — aucune configuration locale requise.
Toutes les leçons de ce cours
- Immutabilité des chaînes et pool de chaînes
- StringBuilder pour une concaténation efficace
- Blocs de texte et String.format
- Expressions régulières avec Pattern et Matcher