Эквивалентность Unicode — это спецификация стандарта кодировки символов Unicode , согласно которой некоторые последовательности кодовых точек представляют по сути один и тот же символ. Эта функция была введена в стандарт для обеспечения совместимости с уже существующими стандартными наборами символов , которые часто включали похожие или идентичные символы.
Unicode предоставляет два таких понятия: каноническая эквивалентность и совместимость. Предполагается, что последовательности кодовых точек , которые определены как канонически эквивалентные, имеют одинаковый внешний вид и значение при печати или отображении. Например, кодовая точка U+006E n ЛАТИНСКАЯ СТРОЧНАЯ БУКВА N , за которой следует U+0303 ◌̃ ОБЪЕДИНЯЮЩАЯСЯ ТИЛЬДА, определяется Unicode как канонически эквивалентная одиночной кодовой точке U+00F1 ñ ЛАТИНСКАЯ СТРОЧНАЯ БУКВА N С ТИЛЬДОЙ испанского алфавита ). Поэтому эти последовательности должны отображаться одинаково, должны обрабатываться одинаково такими приложениями, как упорядочивание имен по алфавиту или поиск , и могут заменять друг друга. Аналогично, каждый блок слогов хангыль , который кодируется как один символ, может быть эквивалентно кодирован как комбинация начального соединительного jamo, гласного соединительного jamo и, при необходимости, конечного соединительного jamo.
Последовательности, которые определены как совместимые , как предполагается, имеют возможно различный внешний вид, но одинаковое значение в некоторых контекстах. Так, например, кодовая точка U+FB00 ( типографская лигатура "ff") определяется как совместимая, но не канонически эквивалентная последовательности U+0066 U+0066 (две латинские буквы "f"). Совместимые последовательности могут обрабатываться одинаково в некоторых приложениях (таких как сортировка и индексация ), но не в других; и могут заменять друг друга в некоторых ситуациях, но не в других. Последовательности, которые канонически эквивалентны, также совместимы, но обратное не обязательно верно.
Стандарт также определяет процедуру нормализации текста , называемую нормализацией Unicode , которая заменяет эквивалентные последовательности символов так, что любые два текста, которые эквивалентны, будут сведены к одной и той же последовательности кодовых точек, называемой формой нормализации или нормальной формой исходного текста. Для каждого из двух понятий эквивалентности Unicode определяет две нормальные формы, одну полностью составленную (где несколько кодовых точек заменяются одиночными точками, когда это возможно), и одну полностью разложенную (где одиночные точки разбиваются на несколько).
Для совместимости или по другим причинам Unicode иногда назначает две разные кодовые точки сущностям, которые по сути являются одним и тем же символом. Например, символ "Å" может быть закодирован как U+00C5 (стандартное название "ЛАТИНСКАЯ ЗАГЛАВНАЯ БУКВА A С КОЛЬЦОМ НАД ВЕРХУ", буква алфавита в шведском и нескольких других языках ) или как U+212B ("ЗНАК АНГСТРОМА"). Тем не менее, символ для ангстрема определен как эта шведская буква, и большинство других символов, которые являются буквами (например, "V" для вольта ) не имеют отдельной кодовой точки для каждого использования. В общем, кодовые точки действительно идентичных символов (которые могут быть отображены одинаково в шрифтах Unicode) определяются как канонически эквивалентные.
Для соответствия некоторым старым стандартам Unicode предоставляет отдельные кодовые точки для многих символов, которые можно рассматривать как измененные формы других символов (например, U+00F1 для «ñ» или U+00C5 для «Å») или как комбинации двух или более символов (например, U+FB00 для лигатуры «ff» или U+0132 для голландской буквы « IJ »).
Для согласованности с другими стандартами и для большей гибкости Unicode также предоставляет коды для многих элементов, которые не используются сами по себе, а предназначены для модификации или объединения с предшествующим базовым символом. Примерами таких комбинируемых символов являются комбинируемая тильда и японский диакритический знак дакутэн ("◌゛", U+3099).
В контексте Unicode композиция символов — это процесс замены кодовых точек базовой буквы, за которой следует один или несколько объединяющих символов, в один предварительно составленный символ ; а разложение символов — это противоположный процесс.
В общем случае составные символы определяются как канонически эквивалентные последовательности их базовой буквы и последующих комбинационных диакритических знаков, в каком бы порядке они ни располагались.
Некоторые письменности регулярно используют несколько комбинирующих знаков, которые, как правило, не взаимодействуют типографически и не имеют предсоставленных символов для комбинаций. Пары таких невзаимодействующих знаков могут храниться в любом порядке. Эти альтернативные последовательности, как правило, канонически эквивалентны. Правила, определяющие их последовательность в канонической форме, также определяют, считаются ли они взаимодействующими.
Unicode предоставляет кодовые точки для некоторых символов или групп символов, которые изменяются только по эстетическим причинам (например, лигатуры , символы катаканы половинной ширины или латинские буквы полной ширины для использования в японских текстах) или для добавления новой семантики без потери исходной (например, цифры в подстрочных или надстрочных позициях или обведенные цифры (например, «①»), унаследованные от некоторых японских шрифтов). Такая последовательность считается совместимой с последовательностью исходных (отдельных и неизмененных) символов для преимуществ приложений, где внешний вид и добавленная семантика не имеют значения. Однако эти две последовательности не объявляются канонически эквивалентными, поскольку различие имеет некоторое семантическое значение и влияет на отображение текста.
UTF-8 и UTF-16 (а также некоторые другие кодировки Unicode) не допускают все возможные последовательности кодовых единиц . Различное программное обеспечение преобразует недопустимые последовательности в символы Unicode, используя различные правила, некоторые из которых являются очень потерями (например, превращая все недопустимые последовательности в один и тот же символ). Это можно считать формой нормализации, и это может привести к тем же трудностям, что и другие.
Программное обеспечение для обработки текста, реализующее функцию поиска и сравнения строк Unicode, должно учитывать наличие эквивалентных кодовых точек. При отсутствии этой функции пользователи, ищущие определенную последовательность кодовых точек, не смогут найти другие визуально неразличимые глифы, имеющие другое, но канонически эквивалентное представление кодовой точки.
Unicode предоставляет стандартные алгоритмы нормализации, которые создают уникальную (нормальную) последовательность кодовых точек для всех последовательностей, которые эквивалентны; критерии эквивалентности могут быть либо каноническими (NF), либо совместимыми (NFK). Поскольку можно произвольно выбирать представительный элемент класса эквивалентности , для каждого критерия эквивалентности возможны множественные канонические формы. Unicode предоставляет две нормальные формы, которые семантически значимы для каждого из двух критериев совместимости: составные формы NFC и NFKC, и разложенные формы NFD и NFKD. Как составные, так и разложенные формы накладывают канонический порядок на последовательность кодовых точек, что необходимо для того, чтобы нормальные формы были уникальными.
Для сравнения или поиска строк Unicode программное обеспечение может использовать как составные, так и разложенные формы; этот выбор не имеет значения, если он одинаков для всех строк, участвующих в поиске, сравнении и т. д. С другой стороны, выбор критериев эквивалентности может повлиять на результаты поиска. Например, некоторые типографские лигатуры, такие как U+FB03 ( ffi ), римские цифры, такие как U+2168 ( Ⅸ ), и даже подстрочные и надстрочные индексы , например U+2075 ( ⁵ ), имеют свои собственные кодовые точки Unicode. Каноническая нормализация (NF) не влияет ни на одну из них, но нормализация совместимости (NFK) разложит лигатуру ffi на составляющие буквы, поэтому поиск U+0066 ( f ) как подстроки будет успешным в нормализации NFKC U+FB03, но не в нормализации NFC U+FB03. Аналогично при поиске латинской буквы I (U+0049) в предкомпозитной римской цифре Ⅸ (U+2168). Аналогично верхний индекс ⁵ (U+2075) преобразуется в 5 (U+0035) с помощью сопоставления совместимости.
Однако преобразование надстрочных знаков в эквиваленты базовой линии может оказаться неподходящим для программного обеспечения для работы с расширенным текстом , поскольку информация о надстрочном знаке теряется в процессе. Чтобы обеспечить это различие, база данных символов Unicode содержит теги форматирования совместимости , которые предоставляют дополнительные сведения о преобразовании совместимости. [1] В случае типографских лигатур этот тег просто <compat>
, тогда как для надстрочного знака это <super>
. Стандарты расширенного текста, такие как HTML, учитывают теги совместимости. Например, HTML использует собственную разметку для размещения U+0035 в позиции надстрочного знака. [2]
Четыре формы нормализации Unicode и алгоритмы (преобразования) для их получения перечислены в таблице ниже.
Все эти алгоритмы являются идемпотентными преобразованиями, что означает, что строка, которая уже находится в одной из этих нормализованных форм, не будет изменена при повторной обработке тем же алгоритмом.
Нормальные формы не закрываются при конкатенации строк . [3] Для дефектных строк Unicode, начинающихся с гласной хангыль или завершающей соединительной буквы jamo , конкатенация может нарушить композицию.
Однако они не являются инъективными (они отображают различные исходные глифы и последовательности в одну и ту же нормализованную последовательность) и, таким образом, также не являются биективными (не могут быть восстановлены). Например, различные строки Unicode "U+212B" (знак ангстрема "Å") и "U+00C5" (шведская буква "Å") обе расширяются NFD (или NFKD) в последовательность "U+0041 U+030A" (латинская буква "A" и объединяющее кольцо над "°"), которая затем сокращается NFC (или NFKC) до "U+00C5" (шведская буква "Å").
Отдельный символ (кроме блока слогов хангыль), который будет заменен другим при нормализации, можно определить в таблицах Unicode по наличию непустого поля совместимости, но отсутствию тега совместимости.
Канонический порядок в основном касается порядка последовательности комбинируемых символов. Для примеров в этом разделе мы предполагаем, что эти символы являются диакритическими знаками , хотя в целом некоторые диакритические знаки не являются комбинируемыми символами, а некоторые комбинируемые символы не являются диакритическими знаками.
Unicode назначает каждому символу класс комбинирования , который идентифицируется числовым значением. Некомбинированные символы имеют номер класса 0, в то время как комбинированные символы имеют положительное значение класса комбинирования. Для получения канонического порядка каждая подстрока символов, имеющая ненулевое значение класса комбинирования, должна быть отсортирована по значению класса комбинирования с использованием стабильного алгоритма сортировки . Стабильная сортировка требуется, поскольку предполагается, что комбинированные символы с одинаковым значением класса взаимодействуют типографически, поэтому два возможных порядка не считаются эквивалентными.
Например, символ U+1EBF (ế), используемый во вьетнамском языке , имеет как акут, так и циркумфлекс. Его каноническое разложение — это последовательность из трех символов U+0065 (e) U+0302 (циркумфлекс) U+0301 (акут). Объединенные классы для двух акцентов — оба 230, поэтому U+1EBF не эквивалентен U+0065 U+0301 U+0302.
Поскольку не все последовательности комбинирования имеют предварительно составленный эквивалент (последняя в предыдущем примере может быть сокращена только до U+00E9 U+0302), даже обычная форма NFC подвержена влиянию поведения символов комбинирования.
Когда два приложения совместно используют данные Unicode, но нормализуют их по-разному, могут возникнуть ошибки и потеря данных. В одном конкретном случае OS X нормализовала имена файлов Unicode, отправленные из программного обеспечения Netatalk и Samba для обмена файлами и принтерами. Netatalk и Samba не распознали измененные имена файлов как эквивалентные исходным, что привело к потере данных. [4] [5] Решение такой проблемы нетривиально, поскольку нормализация не является обратимой без потерь.