Справочный раздел

Unicode и кодировки: UTF‑8, UTF‑16 и кодовые точки

Кодовые точки, байты UTF‑8, единицы UTF‑16, нормализация, BOM и диагностика ошибок кодировки.

От текста к байтам

Четыре разных уровня

  1. ГрафемаТо, что воспринимает читатель: A, é или 👩‍💻.
  2. Кодовая точкаАбстрактный номер Unicode, например U+1F600.
  3. Кодовая единицаШаг хранения: 8 бит в UTF‑8, 16 бит в UTF‑16.
  4. БайтФактическое значение в файле или сетевом потоке.
Таблица кодирования

Один текст на каждом уровне

Копируйте сам знак, кодовые точки, байты UTF‑8 или единицы UTF‑16. Отдельные значения разделены пробелами.

Примеры Unicode с байтами UTF‑8 и единицами UTF‑16
Знак Кодовая точка UTF‑8 UTF‑16 Что показывает
Отдельные кодовые точкиОдин знак Unicode может занимать от одного до четырёх байтов в UTF‑8. 6
Латинская AASCII входит в UTF‑8 без изменений и занимает один байт.
Кириллическая ЯБольшинство кириллических букв кодируется двумя байтами UTF‑8.
Составная éГотовая буква с диакритикой представлена одной кодовой точкой.
Знак евроЗнак из базовой многоязычной плоскости занимает три байта UTF‑8.
Иероглиф 中Типичный иероглиф CJK также занимает три байта UTF‑8.
ЭмодзиКодовая точка вне BMP: четыре байта UTF‑8 и суррогатная пара UTF‑16.
ПоследовательностиОдин видимый знак может состоять из нескольких кодовых точек. 4
Разложенная éБуква e и комбинируемый акут выглядят как é, но остаются двумя кодовыми точками.
Женщина‑технологДва эмодзи соединены символом ZERO WIDTH JOINER U+200D.
Флаг РоссииФлаг складывается из двух региональных индикаторов, а не из одного символа.
Эмодзи с модификаторомБазовый эмодзи и модификатор оттенка кожи образуют один видимый знак.
Практические рецепты

Объявления, преобразование и нормализация

Копируйте готовые объявления и вызовы API. Каждая группа отвечает за отдельный уровень работы с кодировкой.

Рецепты для Unicode и кодировок
ЗадачаКод или байтыКогда использовать
Веб и HTMLКак объявить UTF‑8 и записать символ без прямого ввода.3
Кодировка HTML Помещайте в начале head, чтобы браузер сразу декодировал документ как UTF‑8.
HTTP-заголовок Серверное объявление кодировки ответа; должно совпадать с фактическими байтами.
Числовая HTML-ссылка Записывает кодовую точку в HTML. Это синтаксис разметки, а не отдельная кодировка.
JavaScriptПреобразование строк в байты и создание символов по кодовой точке.3
Строка → UTF‑8 Возвращает Uint8Array с байтами UTF‑8.
UTF‑8 → строка Декодирует байты; fatal: true превращает неверную последовательность в ошибку.
Кодовая точка → символ Создаёт 😀 без ручной записи суррогатной пары UTF‑16.
НормализацияПриведение эквивалентных последовательностей к предсказуемой форме.3
NFC: составная форма Обычный выбор для хранения, сравнения и обмена текстом без потери различий совместимости.
NFD: разложенная форма Разделяет составные символы на основу и комбинируемые знаки.
NFKC: совместимость Складывает совместимые варианты вроде полноширинных форм; применяйте только когда допустима потеря таких различий.
BOM и порядок байтовСигнатуры в начале потока; для UTF‑8 BOM обычно не требуется.3
BOM UTF‑8 Сигнатура UTF‑8. Порядка байтов у UTF‑8 нет, поэтому добавляйте её только когда требует формат или программа.
BOM UTF‑16LE Указывает порядок байтов от младшего к старшему для UTF‑16.
BOM UTF‑16BE Указывает порядок байтов от старшего к младшему для UTF‑16.
Расшифровка кракозябр

О чём говорит повреждённый текст

Видимый рисунок часто указывает на место ошибки, но возможность восстановления зависит от сохранности исходных байтов.

Привет Байты UTF‑8 прочитаны как Windows‑1251.

Вернитесь к исходным байтам и декодируйте их как UTF‑8; не перекодируйте уже испорченную строку вслепую.

Привет Байты UTF‑8 прочитаны как Windows‑1252 или совместимая однобайтовая кодировка.

Проверьте charset в HTTP, HTML и настройках импорта файла.

������ Декодер встретил недопустимые байты и подставил U+FFFD REPLACEMENT CHARACTER.

Найдите исходный файл или поток: после замены на � восстановить потерянные байты по строке обычно нельзя.

?????? Текст сохранили в кодировке, которая не умеет представить нужные символы.

Перейдите на UTF‑8 до записи. Если символы уже заменены вопросами, нужен исходный текст или резервная копия.

Короткая памятка

Сохраняйте текст на всех границах

По умолчанию выбирайте UTF‑8
Используйте UTF‑8 для новых файлов, API, баз данных и веб-страниц и одинаково объявляйте её на всех границах.
Сохраняйте исходные байты
Если текст повреждён, сначала определите кодировку байтов и только потом сохраняйте или перекодируйте видимую строку.
Нормализуйте осознанно
NFC подходит как практическая форма для сравнения; NFKC стирает совместимые различия и не является универсальной очисткой.
Считайте видимые знаки
Длина строки, число кодовых точек и число графем могут различаться у эмодзи и комбинируемых последовательностей.

Рекомендации по кодировкам сверены со WHATWG Encoding Standard; нормализация и поведение BOM — с документами Unicode Normalization Forms и Unicode UTF & BOM FAQ.

Связанные инструменты

Продолжите работу с текстом

Скопируйте символ, преобразуйте разметку, очистите фрагмент или сохраните результат в блокноте.

FAQ

Вопросы о Unicode и кодировках

Чем Unicode отличается от UTF‑8?

Unicode назначает символам абстрактные кодовые точки. UTF‑8 — один из способов записать их байтами. UTF‑16 и UTF‑32 — другие формы кодирования.

Почему в JavaScript длина "😀" равна 2?

Строки JavaScript представлены единицами UTF‑16. U+1F600 находится вне базовой многоязычной плоскости и записывается суррогатной парой — двумя кодовыми единицами.

Нужен ли BOM в файле UTF‑8?

Обычно нет: в UTF‑8 нет неоднозначности порядка байтов. BOM может быть сигнатурой, но добавлять его стоит только по требованию формата или программы.

Всегда ли можно исправить кракозябры?

Только если сохранились исходные байты или обратимая цепочка ошибочных преобразований. Символы замены и вопросительные знаки часто означают, что часть информации уже потеряна.

Когда нормализовать текст?

Делайте это на выбранной границе системы, обычно в NFC перед хранением или сравнением. Не применяйте совместимую нормализацию многократно к произвольному содержимому.