Строка Максимальная длина в Java - метод length()

Мой вопрос очень простой, но я не нашел ответа на поиск в Google.

В Java, каков максимальный размер объекта String, ссылаясь на вызов метода length()?

Я знаю, что length() возвращает размер String как char [];

Ответ 1

Учитывая String class 'length возвращает int, максимальная длина, возвращаемая методом, будет Integer.MAX_VALUE, которая равна 2^31 - 1 (или около 2 миллиардов.)

В терминах длины и индексации массивов (например, char[], что, вероятно, является способом представления внутренних данных для String s), Глава 10: Массивы Спецификация Java Language, Java SE 7 Edition гласит следующее:

Переменные, содержащиеся в массиве не имеют имен; вместо этого они ссылки на выражения доступа к массиву которые используют неотрицательный целочисленный индекс значения. Эти переменные называются компоненты массива. Если массив имеет компоненты n, мы говорим, что n - это длина массива; компоненты массив ссылается с использованием целого числа индексы от 0 до n - 1 включительно.

Кроме того, индексирование должно иметь значения int, как указано в Раздел 10.4:

Массивы должны индексироваться значениями int;

Следовательно, оказывается, что предел действительно 2^31 - 1, так как это максимальное значение для неотрицательного значения int.

Однако, вероятно, будут другие ограничения, такие как максимальный размер выделяемого массива.

Ответ 2

Так как массивы должны индексироваться с целыми числами, максимальная длина массива равна Integer.MAX_INT (2 31 -1 или 2 147 483 647). Это предполагает, что у вас достаточно памяти для хранения массива такого размера, конечно.

Ответ 3

java.io.DataInput.readUTF() и java.io.DataOutput.writeUTF(String) говорят, что объект String представлен двумя байтами информации о длине и измененным UTF-8 представление каждого символа в строке. Это делает вывод о том, что длина строки ограничена количеством байтов модифицированного представления строки UTF-8 при использовании с DataInput и DataOutput.

Кроме того, Спецификация CONSTANT_Utf8_info, найденная в спецификации виртуальной машины Java, определяет структуру следующим образом.

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

Вы можете найти, что размер "длина" два байта.

То, что тип возврата определенного метода (например, String.length()) составляет int, не всегда означает, что его допустимое максимальное значение равно Integer.MAX_VALUE. Вместо этого, в большинстве случаев, int выбирается только по соображениям производительности. Спецификация языка Java говорит, что целые числа, размер которых меньше, чем int, преобразуются в int перед вычислением (если моя память служит мне правильно), и это одна из причин выбора int, когда нет особой причины.

Максимальная длина во время компиляции не более 65536. Заметим еще раз, что длина представляет собой количество байтов измененного представления UTF-8, а не количество символов в объекте String.

String объекты могут иметь гораздо больше символов во время выполнения. Однако, если вы хотите использовать объекты String с интерфейсами DataInput и DataOutput, лучше избегать использования слишком длинных объектов String. Я нашел это ограничение, когда я внедрил Objective-C эквиваленты DataInput.readUTF() и DataOutput.writeUTF(String).

Ответ 4

по-видимому, он связан с int, который равен 0x7FFFFFFF (2147483647).

Ответ 5

Тип возвращаемого значения метода length() класса String int.

public int length()

Обратитесь http://docs.oracle.com/javase/7/docs/api/java/lang/String.html#length()

Таким образом, максимальное значение int 2147483647.

Строка считается внутренним массивом char, поэтому индексирование выполняется в пределах максимального диапазона. Это означает, что мы не можем индексировать 2147483648-й член. Таким образом, максимальная длина строки в java равна 2147483647.

Примитивный тип данных int - 4 байта (32 бита) в java. В качестве знакового бита используется 1 бит (MSB). Диапазон ограничен в пределах от -2 ^ 31 до 2 ^ 31-1 (-2147483648 до 2147483647).). Мы не можем использовать отрицательные значения для индексации. Очевидно, что диапазон, который мы можем использовать, составляет от 0 до 2147483647.

Ответ 6

У меня есть iMac 2010 года с 8 ГБ ОЗУ, запускающий Eclipse Neon.2 Release (4.6.2) с Java 1.8.0_25. С аргументом VM -Xmx6g я выполнил следующий код:

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());

Отпечатки:

Requested array size exceeds VM limit
1207959550

Итак, кажется, что максимальный размер массива составляет ~ 1207,959,549. Затем я понял, что на самом деле нам неинтересно, что в Java заканчивается память: мы просто ищем максимальный размер массива (который, как представляется, определен как константа). Итак:

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);
    }
}

Какие принты:

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

Итак, кажется, что max является Integer.MAX_VALUE - 2, или (2 ^ 31) - 3

P.S. Я не уверен, почему мой StringBuilder достиг максимума в 1207959550, а мой char[] превысил отметку (2 ^ 31) -3. Кажется, что AbstractStringBuilder удваивает размер своего внутреннего char[], чтобы увеличить его, что, вероятно, вызывает проблему.