En fait, les raisons pour lesquelles les chaînes sont immuables en Java n'ont pas grand-chose à voir avec la sécurité. Les deux principales raisons sont les suivantes :
Sécurité de la théade :
Les chaînes de caractères sont un type d'objet extrêmement répandu. Il est donc plus ou moins garanti qu'elles seront utilisées dans un environnement multithread. Les chaînes de caractères sont immuables afin de garantir la sécurité du partage des chaînes de caractères entre les threads. Le fait d'avoir des chaînes immuables garantit que, lors du passage de chaînes du thread A à un autre thread B, le thread B ne peut pas modifier inopinément la chaîne du thread A.
Cela permet non seulement de simplifier la tâche déjà assez compliquée de la programmation multithread, mais aussi d'améliorer les performances des applications multithread. L'accès aux objets mutables doit être synchronisé d'une manière ou d'une autre lorsqu'ils sont accessibles à partir de plusieurs threads, afin de s'assurer qu'un thread ne tente pas de lire la valeur de votre objet pendant qu'il est modifié par un autre thread. Une synchronisation appropriée est à la fois difficile à réaliser correctement pour le programmeur et coûteuse au moment de l'exécution. Les objets immuables ne peuvent pas être modifiés et n'ont donc pas besoin de synchronisation.
Performance :
Bien que l'internage des chaînes de caractères ait été mentionné, il ne représente qu'un faible gain d'efficacité mémoire pour les programmes Java. Seuls les littéraux de chaîne sont internés. Cela signifie que seules les chaînes de caractères qui sont les mêmes dans votre fichier code source partageront le même String Object. Si votre programme crée dynamiquement des chaînes qui sont identiques, elles seront représentées dans des objets différents.
Plus important encore, les chaînes immuables leur permettent de partager leurs données internes. Pour de nombreuses opérations sur les chaînes, cela signifie que le tableau de caractères sous-jacent ne doit pas être copié. Par exemple, disons que vous voulez prendre les cinq premiers caractères de String. En Java, vous appelleriez maChaîne.substring(0,5). Dans ce cas, la méthode substring() crée simplement un nouvel objet String qui partage le char[] sous-jacent de myString mais qui sait qu'il commence à l'indice 0 et se termine à l'indice 5 de ce char[]. Pour exprimer cela sous forme graphique, vous obtiendrez ce qui suit :
| myString |
v v
"The quick brown fox jumps over the lazy dog" <-- shared char[]
^ ^
| | myString.substring(0,5)
Cela rend ce type d'opérations extrêmement bon marché, et O(1) puisque l'opération ne dépend ni de la longueur de la chaîne originale, ni de la longueur de la sous-chaîne que nous devons extraire. Ce comportement présente également des avantages en termes de mémoire, puisque de nombreuses chaînes de caractères peuvent partager leur char[] sous-jacent.
13 votes
J'ai eu la même pensée, mais j'ai vérifié l'emplacement des posters originaux et j'ai trouvé qu'ils sont de Belgique. Cela signifie qu'il est peu probable qu'il soit de langue maternelle anglaise. Si l'on ajoute à cela le fait que la plupart des natifs ont une connaissance approximative de la langue, j'ai décidé de la laisser tranquille.
8 votes
Merci belugabob, mais je ne suis pas une elle, je suis un lui. Apparemment, les gens ne tiennent pas compte des différences culturelles.
7 votes
Mes excuses - chrissie est (généralement) un nom de fille au Royaume-Uni - ce qui fait de moi une victime d'une autre différence culturelle :-)
2 votes
Juste une remarque, dans .NET
String
est en fait mutable en interne.StringBuilder
dans .NET 2.0 modifie une chaîne de caractères . Je vais juste le laisser ici.0 votes
En fait, les chaînes de caractères .NET sont mutable. Et ce n'est même pas une sacrée pirouette.