160 votes

Longueur maximale d'une chaîne de caractères en Java - appel de la méthode length()

Sur Java quelle est la taille maximale d'une String peut avoir, en se référant à la length() l'appel de la méthode ?

Je sais que length() retourner la taille d'un String en tant que char [] ;

6 votes

Alors que la longueur d'un String est théoriquement Integer.MAX_VALUE la longueur d'une chaîne de caractères littérale dans la source semble être limitée à uniquement 65535 octets de données UTF-8.

175voto

coobird Points 70356

Considérant le String classe [length](http://docs.oracle.com/javase/7/docs/api/java/lang/String.html#length()) renvoie un int la longueur maximale qui serait retournée par la méthode serait la suivante Integer.MAX_VALUE qui est 2^31 - 1 (soit environ 2 milliards).

En termes de longueur et d'indexation des tableaux, (tels que char[] ce qui est probablement la façon dont la représentation interne des données est mise en œuvre pour les systèmes d'information de l'UE. String s), Chapitre 10 : Les tableaux de La spécification du langage Java, édition Java SE 7 dit ce qui suit :

Les variables contenues dans un tableau n'ont pas de nom ; elles sont référencées par des expressions d'accès au tableau qui utilisent des valeurs d'index entières non négatives entiers non négatifs. Ces variables sont appelées composants du tableau. Si un tableau a n les composants, nous disons n est le longueur du tableau ; les composantes du le tableau est référencé à l'aide d'indices entiers entiers de 0 à n - 1 inclusivement.

En outre, l'indexation doit se faire par int comme mentionné dans Section 10.4 :

Les tableaux doivent être indexés par int valeurs ;

Par conséquent, il semble que la limite soit effectivement 2^31 - 1 car c'est la valeur maximale d'une valeur non négative. int valeur.

Cependant, il y aura probablement d'autres limitations, comme la taille maximale allouable pour un tableau.

30 votes

Integer.MAX_VALUE est 2^31-1, en fait :)

0 votes

Vous avez tout à fait raison ! Merci de le signaler, j'ai corrigé ma réponse.

1 votes

Super réponse, mec ! J'ai jeté un coup d'oeil sur le code source de String.java et c'est vrai, 'count' est la variable int qui retourne la longueur du tableau de chars, et le tableau de chars est stocké sur la variable 'value' (comme char [ ]) Cela signifie que la taille du String pourrait être autour de 2GB. Bien sûr, il pourrait y avoir des limitations pour allouer une telle taille de mémoire. Merci !

27voto

Takahiko Kawasaki Points 1313

[java.io.DataInput.readUTF()](http://docs.oracle.com/javase/7/docs/api/java/io/DataInput.html#readUTF%28%29) et [java.io.DataOutput.writeUTF(String)](http://docs.oracle.com/javase/7/docs/api/java/io/DataOutput.html#writeUTF%28java.lang.String%29) dire qu'un String est représenté par deux octets d'informations sur la longueur et le UTF-8 modifié représentation de chaque caractère de la chaîne. Ceci conclut que la longueur de la chaîne de caractères est limitée par le nombre d'octets de la représentation UTF-8 modifiée de la chaîne de caractères lorsqu'elle est utilisée avec la fonction DataInput et DataOutput .

En outre, La spécification de CONSTANT_Utf8_info trouvée dans la spécification de la machine virtuelle Java définit la structure comme suit.

CONSTANT_Utf8_info {
    u1 tag;
    u2 length;
    u1 bytes[length];
}

Vous pouvez constater que la taille de 'longueur' est de deux octets .

Que le type de retour d'une certaine méthode (par exemple String.length() ) est int ne signifie pas toujours que sa valeur maximale autorisée est Integer.MAX_VALUE . Au lieu de cela, dans la plupart des cas, int est choisi uniquement pour des raisons de performance. La spécification du langage Java indique que les entiers dont la taille est inférieure à celle de int sont convertis en int avant le calcul (si ma mémoire est bonne) et c'est une des raisons pour lesquelles il faut choisir int lorsqu'il n'y a pas de raison particulière.

La longueur maximale au moment de la compilation est de 65536 au maximum. Notez encore une fois que la longueur est le nombre d'octets de l'objet UTF-8 modifié et non le nombre de caractères d'une String objet.

String Les objets peuvent avoir beaucoup plus de caractères au moment de l'exécution. Cependant, si vous souhaitez utiliser String des objets avec DataInput et DataOutput Il vaut mieux éviter d'utiliser des interfaces trop longues. String des objets. J'ai découvert cette limitation lorsque j'ai implémenté les équivalents Objective-C de DataInput.readUTF() et DataOutput.writeUTF(String) .

1 votes

Cela devrait être la réponse par défaut.

20voto

Michael Myers Points 82361

Puisque les tableaux doivent être indexés avec des entiers, la longueur maximale d'un tableau est de Integer.MAX_INT (2 31 -1, soit 2 147 483 647). Cela suppose que vous ayez suffisamment de mémoire pour contenir un tableau de cette taille, bien sûr.

14voto

dantiston Points 56

J'ai un iMac 2010 avec 8 Go de RAM, exécutant Eclipse Neon.2 Release (4.6.2) avec Java 1.8.0_25. Avec l'argument VM -Xmx6g, j'ai exécuté le code suivant :

StringBuilder sb = new StringBuilder();
for (int i = 0; i < Integer.MAX_VALUE; i++) {
    try {
        sb.append('a');
    } catch (Throwable e) {
        System.out.println(i);
        break;
    }
}
System.out.println(sb.toString().length());

Cette empreinte :

Requested array size exceeds VM limit
1207959550

Il semble donc que la taille maximale du tableau soit de ~1,207,959,549. Puis j'ai réalisé que nous ne nous soucions pas vraiment de savoir si Java manque de mémoire : nous cherchons simplement la taille maximale du tableau (qui semble être une constante définie quelque part). Donc :

for (int i = 0; i < 1_000; i++) {
    try {
        char[] array = new char[Integer.MAX_VALUE - i];
        Arrays.fill(array, 'a');
        String string = new String(array);
        System.out.println(string.length());
    } catch (Throwable e) {
        System.out.println(e.getMessage());
        System.out.println("Last: " + (Integer.MAX_VALUE - i));
        System.out.println("Last: " + i);
    }
}

Qui imprime :

Requested array size exceeds VM limit
Last: 2147483647
Last: 0
Requested array size exceeds VM limit
Last: 2147483646
Last: 1
Java heap space
Last: 2147483645
Last: 2

Il semble donc que le maximum soit Integer.MAX_VALUE - 2, ou (2^31) - 3.

P.S. Je ne suis pas sûr de savoir pourquoi mon StringBuilder a atteint son maximum à 1207959550 alors que mon char[] a atteint son maximum à (2^31)-3. Il semble que AbstractStringBuilder double la taille de son char[] pour le cultiver, ce qui cause probablement le problème.

2 votes

Un traitement pratique très utile de la question

5voto

Francis Points 4305

Apparemment il est lié à un int, qui est 0x7FFFFFFF (2147483647).

Prograide.com

Prograide est une communauté de développeurs qui cherche à élargir la connaissance de la programmation au-delà de l'anglais.
Pour cela nous avons les plus grands doutes résolus en français et vous pouvez aussi poser vos propres questions ou résoudre celles des autres.

Powered by:

X