Comments 33
— Для использования компактных строк от программиста не требуется ничего, кроме запуска приложения под джавой 9.
— Для русского языка компактные строки не дадут ни байта выигрыша.
М-да…
Скажите, я правильно понял: внутри компактные строки хранят utf-8? А каков проигрыш в производительности при использовании строк с кириллицей — ведь их придется кодировать-декодировать при любых манипуляциях? А каков будет «выигрыш» при использовании, скажем, строк индийских символов или китайских иероглифов, где один символ может кодироваться в urf-8 тремя, четырьмя, а то и пятью байтами?
Другими словами, эта функция заменяет значение в массиве char (где каждый элемент использует 2 байта) байтовым массивом с дополнительным байтом для определения кодировки (Latin-1 или UTF-16).
Вопрос снимается, голова пеплом посыпается.
Остается не очень понятно, зачем под битовый флажок отвели целый байт, ну да ладно.
Почему не бит — вопрос в том как его хранить с кем его есть — опять же — бенчмарки показали, что так (с флагом) будет лучше.
Остается не очень понятно, зачем под битовый флажок отвели целый байт, ну да ладно.А как вы себе представляете размещение отдельного бита в памяти?
Отдельный бит можно запихать в уже существующее поле флагов, если таковое есть.
Можно, посмотрели, это всё не взлетело. Кроме того, добавление байтового поля реально не увеличило затрат памяти из-за уже существующего до этого выравнивания. Подробности можно увидеть по ссылка в этом комментарии.
один символ может кодироваться в urf-8 тремя, четырьмя, а то и пятью байтами
Разве где-то сейчас используется UTF-8 с символами больше 4 байт?
Вроде в RFC 3629, который является официальным стандартом, указано, что «In UTF-8, characters from the U+0000..U+10FFFF range are encoded using sequences of 1 to 4 octets». И символы за пределами этого range запрещены («Restricted the range of characters to 0000-10FFFF»).
Но в предыдущей (давно устаревшей) версии стандарта (rfc2279) были возможны символы, требующие до 6 байт.
Или я что-то упускаю?
Нет, и не переедут. Это поломает существующее API
UTF-16 со своими суррогатными парами даёт ложную надежду, но всё равно не позволяет бегать по индексу. Для того, чтобы обращаться по индексу к строке с эмодзи нужна отдельная функция. Строка — не массив, в любой кодировке.
Utf8 совместим с ascii, utf16 нет.
Для ascii строк он в два раза выгоднее, чем utf16.
У utf8 нет проблемы с BE/LE.
Оба не позволяют индексировать строку, в отличие от utf32.
Так что не все так однозначно.
P.S. хабр вообще порезал сообщение, встретив символ этого флага (ну или firefox плохо закодировал): emojipedia.org/flag-for-england
Максимальное значение одного символа — 0x10FFFF. Это около 21 бит. Следовательно в кодировке utf32 каждый символ занимает вмещается в 4 байта, и индексация вполне работает.
Так как для разных задач используются разные UTF.
- UTF-8 — выгодно хранить текст. Совместима с ascii, нормально работает в старых программах и компиляторах как нуль-терминальная строка.
- UTF-16 — удобно использовать в программировании, так как размер массива, как правило, равен количеству символов, по крайней мере для латинского/кириллического алфавита и спецсимволов.
- UTF-32 — можно использовать как массив символов, удобно в работе с обработкой текста (поиском и т.д).
Господи, почему в 2к18 ещё не все переехали на UTF-8?
В Джаве есть класс String. Его методы используются в большом количестве софта. В частности используется метод charAt(int index). В частности он используется внутри циклов. Если перейти на utf-8 (что в общем прекрасная идея) — алгоритмическая сложность charAt станет линейной, а сложность методов, в которых есть циклы — квадратичной. На это пойти никак нельзя.
Суть данного треда как раз в том, что сложность charAt константна только для 1-байтных кодировок
А суть моего комментария в том, что charAt возвращает не codePoint а значение типа char, которое берётся прямиком из массива типа char, который находится под капотом у строки )). И куча народу этим пользуется. И ломать код этих людей нельзя, хотя он, возможно и не вполне корректный.
Компактные строки в Java 9