Што такое нармаваны UTF-8 все?

ICU праект (які зараз таксама мае бібліятэка PHP ) змяшчае класы, неабходныя, каб дапамагчы нармалізаваць UTF-8 радкоў, каб зрабіць яго прасцей для параўнання значэнняў пры пошуку.

Тым не менш, я спрабую высветліць, , што гэта азначае для прыкладанняў. Напрыклад, у якіх выпадках я хачу «Canonical эквівалентнасці» замест «эквівалентнасці сумяшчальнасці», або Vis-Versa?

116
@ObscureRobot Я сапраўды хачу ведаць, ці могуць гэтыя дадатковыя сімвалы маюць стан ці няма
дададзена аўтар Eonil, крыніца
@ObscureRobot Напрыклад, нейкі момант такі код: (пачаць выгнутую лінію) (char1) (char2) ... (Чорная) (канец выгнутай лініі) , а не так: (прэфікс маркера выгнутая лінія ) (char1) (выгнутыя лініі маркерам прэфікс) (char2) (выгнутыя лініі маркера прэфікс) (char2) . Іншымі словамі, мінімальная адзінка, якая можа быць аказана?
дададзена аўтар Eonil, крыніца
Гэта гучыць як добры пытанне самастойна.
дададзена аўтар ObscureRobot, крыніца
@Eonil - Я не ўпэўнены, што стан азначае ў кантэксце Юнікода.
дададзена аўтар ObscureRobot, крыніца
Хто ̸͢k̵͟n̴͘ǫw̸̛s͘ w͘͢ḩ̵a҉̡͢t жахі Ляжыце ў Цёмным сэрца Юнікод? ͞
дададзена аўтар ObscureRobot, крыніца

7 адказы

Усё, што вы ніколі не хацелі ведаць пра стандартызацыі Юнікода

Canonical Нармалізацыя

Unicode includes multiple ways to encode some characters, most notably accented characters. Canonical Нармалізацыя changes the code points into a canonical encoding form. The resulting code points should appear identical to the original ones barring any bugs in the fonts or rendering engine.

калі выкарыстоўваць

Because the results appear identical, it is always safe to apply Canonical Нармалізацыя to a string before storing or displaying it, as long as you can tolerate the result not being bit for bit identical to the input.

Canonical Нармалізацыя comes in 2 forms: NFD and NFC. The two are equivalent in the sense that one can convert between these two forms without loss. Comparing two strings under NFC will always give the same result as comparing them under NFD.

NFD

NFD мае характары раскрываюцца цалкам па-за. Гэта хутчэй, нармалізацыя формы для вылічэнні, але вынік у больш кодавых кропак (г.зн. выкарыстоўвае больш прасторы).

Калі вы проста хочаце, каб параўнаць два радкі, якія ўжо не нармалізуецца, гэта з'яўляецца пераважнай формай нармалізацыі, калі вы не ведаеце, што вам патрэбна нармалізацыя сумяшчальнасці.

NFC

NFC перекомбинирует кодавыя кропкі, калі гэта магчыма пасля запуску алгарытму NFD. Гэта зойме трохі больш часу, але прыводзіць да больш кароткім радках.

нармалізацыя Сумяшчальнасць

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

нармалізацыя Сумяшчальнасць converts these to the corresponding sequence of "real" characters, and also performs Canonical Нармалізацыя. The results of нармалізацыя Сумяшчальнасць may not appear identical to the originals.

Сімвалы, якія ўключаюць у сябе інфармацыю аб фарматаванні замяняюцца тыя, якія гэтага не робяць. Напрыклад, сімвал пераўтворыцца ў 9 . Іншыя не мяркуюць фарматаванне адрозненняў. Напрыклад, рымскія лічбы сімвалаў пераўтворыцца ў звычайныя літары IX .

Відавочна, што калі-то гэта пераўтварэнне было выканана, яно ўжо не магчыма без страт пераўтварыць назад да зыходнага набору знакаў.

калі выкарыстоўваць

The Unicode Consortium suggests thinking of нармалізацыя Сумяшчальнасць like a ToUpperCase transform. It is something that may be useful in some circumstances, but you should not just apply it willy-nilly.

Выдатны варыянт выкарыстання будзе пошукавік, так як вы, верагодна, хочаце, пошук 9 , каб адпавядаць .

One thing you should probably not do is display the result of applying нармалізацыя Сумяшчальнасць to the user.

NFKC/NFKD

нармалізацыя Сумяшчальнасць form comes in two forms NFKD and NFKC. They have the same relationship as between NFD and C.

Любы радок у NFKC па сваёй прыродзе таксама ў NFC, і тое ж самае для NFKD і NFD. Такім чынам, NFKD (х) = NFD (NFKC (х)) і NFKC (х) = НКА (NFKD (х)) і г.д.

выснову

If in doubt, go with Canonical Нармалізацыя. Choose NFC or NFD based on the space/speed trade-off applicable, or based on what is required by something you are inter-operating with.

165
дададзена
Вы заўсёды хочаце NFD ўсе радкі на ўваходзе ў першы ж самае, і NFC ўсе радкі вываду, як самае апошняе. Гэта добра вядома.
дададзена аўтар tchrist, крыніца
@Kevin: Так, NFD ў і NFC з знішчаць адзіночка. Я не ўпэўнены, што хто-то клапоціцца пра тых, хто, але, магчыма.
дададзена аўтар tchrist, крыніца
Кароткі даведнік, каб успомніць, што абрэвіятуры пазначаныя: <б> NF = <я> Нармалізаваных форма D = <я> раскладаюцца (распакаванне) , <б> З = <я> кампанаваць (кампрэс) <б> Да = <я> сумяшчальнасць (так як "C" было прынята).
дададзена аўтар Mike Spross, крыніца
«Параўноўваючы два радкі пад NFC заўсёды дае той жа вынік, параўноўваючы іх пад NFD.», Але ў адпаведнасці з нармалізацыя раздзел стабільнасці «[...] калі радок, якая не мае якіх-небудзь неразмеркаваны сімвалы нармалізуецца пад адной версіі Unicode, ён павінен заставацца нармаваныя пры ўсіх будучых версіях Unicode.» Так што, калі Q-гачек ўводзіцца ў больш позняй версіі, і вы спрабуеце параўнаць Q + Caron, які змяшчае радок Q-Caron радок, форма NFC не будзе эквівалентная, але NFD форма павінна. Ці з'яўляецца гэта правільна?
дададзена аўтар Aurimas, крыніца
@tchrist: Гэта, як правіла, добры савет, за выключэннем тых рэдкіх выпадкаў, калі вы жадаеце выхад быць байт у байт ідэнтычнага ўводу, калі ніякія змены не будуць унесены. Ёсць некаторыя іншыя выпадкі, калі вы хочаце NFC ў памяці або па СФО на дыску, але яны з'яўляюцца Exeption, а не правіла.
дададзена аўтар Kevin Cathcart, крыніца
Можна падумаць, што, але з прыкладання: «Для таго, каб пераўтварыць радок Unicode у зададзеную Unicode Нармалізацыя формы, то першы крок, каб цалкам падзяліць радок». Такім чынам, нават wehn працуе NFC, Q-Керон першым стаў бы стаць Q + Caron, і не мог перекомпонуйте, паколькі правілы забараняюць стабільнасць пры даданні новага адлюстравання кампазіцыі. NFC эфектыўна вызначаецца як NFC (х) = перекомпонуйте (NFD (х)) .
дададзена аўтар Kevin Cathcart, крыніца

Некаторыя сімвалы, напрыклад, літары з акцэнтам (напрыклад, é ) можа быць прадстаўлена двума спосабамі - адна кропка кода U + 00E9 або раўніну ліст, за якім варта камбінуючы акцэнт знак U + 0065 U + 0301 . Звычайная нармалізацыя будзе выбіраць адзін з іх заўсёды ўяўляюць яго (у адну кропку кода для NFC, аб'яднанне формы для NFD).

Для сімвалаў, якія могуць быць прадстаўлены мноства паслядоўнасцяў базавых знакаў і камбінаванне знакаў (скажам, «S, кропка ніжэй, кропка над" супраць пакласці кропку вышэй, то кропка ніжэй, або з выкарыстаннем базавага сімвала, які ўжо мае адну з кропак), NFD будзе таксама выбраць адзін з іх (ніжэй ідзе першым, як гэта адбываецца)

Раскладання сумяшчальнасці ўключаюць шэраг сімвалаў, якія "не павінна сапраўды" быць персанажы, але якія, таму што яны былі выкарыстаны ў састарэлых кадоўках. Звычайная нармалізацыя не будзе уніфікаваць гэтыя (для захавання цэласнасці туды-назад - гэта не праблема для аб'ядноўваюцца формаў, таму што няма састарэлага кадавання [за выключэннем некалькіх в'етнамскіх кадовак] не выкарыстоўваецца як), але нармалізацыя сумяшчальнасці будзе. Падумайце, як «кг» кілаграмовага знак, які з'яўляецца ў некаторых краінах Усходняй Азіі кадовак (або полуширина/Полноширинный катакана і алфавіт), або «фі» лігатура ў MacRoman.

См http://unicode.org/reports/tr15/ для атрымання больш падрабязнай інфармацыі.

38
дададзена
Гэта сапраўды правільны адказ. Калі вы выкарыстоўваеце толькі кананічную нармалізацыю тэксту, паўсталі ў некаторым наборы сімвалаў спадчыны, то вынік можа быць ператвораны назад у гэты наборы сімвалаў без страт. Пры выкарыстанні декомпозиции сумяшчальнасці, вы ў канчатковым выніку без якіх-небудзь знакаў сумяшчальнасці, але гэта ўжо не магчыма пераўтварыць назад у зыходны набор сімвалаў без страт.
дададзена аўтар Kevin Cathcart, крыніца

Нармальныя формы (Юнікод, ня базы дадзеных) датычыцца ў першую чаргу (толькі?) З сімваламі, якія маюць дыякрытычны знакі. Unicode змяшчае некаторыя сімвалы з «убудаваным» дыякрытычныя знакі, такія як U + 00C0, «Лацінскай загалоўнай А з Grave». Жа знак можа быць створаны з `лацінскага капіталу A» (U + 0041) з "Аб'ядноўваючы апостраф" (U + 0300). Гэта азначае, што нават пры тым, што дзве паслядоўнасці даюць аднолькавы выніковы характар, байт за байт параўнанне пакажа іх як зусім розныя.

Нармалізацыя ўяўляе сабой спробу барацьбы з гэтым. Нармалізацыя запэўнівае (ці, па меншай меры, спрабуе), што ўсе знакі кадуюцца такім жа чынам - альбо ўсё, выкарыстоўваючы асобны дыякрытычны знак, які спалучае ў выпадку неабходнасці, ці ўсё, выкарыстоўваючы адзіную кропку кода, дзе гэта магчыма. З пункту гледжання параўнання, гэта на самай справе не мае значэння, ўсяго многа, якія вы выбіраеце - амаль любая нармаваная радок будзе параўноўваць правільна з другога нармалізаваць радком.

У гэтым выпадку, «сумяшчальнасць» азначае сумяшчальнасць з кодам, які прадугледжвае, што адзін код пункту роўны аднаму знаку. Калі ў вас ёсць код, які вы, верагодна, хочаце выкарыстоўваць сумяшчальнасці нармальную форму. Хоць я ніколі не бачыў, як гэта паказана прама, імёны нармальных формаў азначаюць, што кансорцыум Unicode лічыць пераважным выкарыстоўваць асобныя дыякрытычны знакі. Для гэтага патрабуецца больш розуму, каб падлічыць фактычныя сімвалы ў радку (а таксама такія рэчы, як разарваць радок разумна), але з'яўляецца больш універсальным.

Калі вы ў поўнай меры выкарыстаць ICU, верагоднасць таго, што вы хочаце выкарыстоўваць кананічную нармальную форму. Калі вы спрабуеце пісаць код на сваім уласным, што (да прыкладу) мяркуе наяўнасць коды роўны сімвал, то вы, верагодна, хочаце сумяшчальнасці нармальнай формы, што робіць, што дакладна як мага часцей.

13
дададзена
Такім чынам, гэта тая частка, дзе графемы Функцыя прыходзіць у той , Мала таго, што персанаж больш байт, чым ASCII - але некалькі паслядоўнасцяў можа быць адзін правы сімвал? (У адрозненне ад MB радок функцый.)
дададзена аўтар Xeoncross, крыніца
@ Random832 Гэта не так. Ваш «прыкладна» занадта там. Разгледзім два Графа, ўшчыльнялых і ȭ. Ёсць шмат шмат спосабаў, каб напісаць кожны з тых, з якіх роўна адзін кожны NFC і адзін NFD, але таксама існуюць і іншыя. Гэта ні адна справа не ў тым, што толькі адзін код кропкі. NFD для першых "аб \ х {332} \ х {303} \ х {304}" і NFC з'яўляецца "\ х {22D} \ х {332}" . Для другога NFD з'яўляецца "аб \ х {332} \ х {304} \ х {303}" і NFC з'яўляецца "\ х {14D} \ х {332} \ х { 303} ". Тым не менш, многія некананічныя існуюць магчымасці, якія кананічна эквівалентныя гэтым. Нармалізацыя дазваляе бінарнае параўнанне кананічны эквівалентных графа.
дададзена аўтар tchrist, крыніца
@ Random832: На жаль, цалкам дакладна. Я павінен ведаць лепш, чым ісці з памяці, калі я не працаваў з ім за апошні год ці два.
дададзена аўтар Jerry Coffin, крыніца
Не, «адзін пункт код адзін знак» прыкладна адпавядае NFC (адзін з спалучалымі пазнакамі NFD, і ні адзін з іх з'яўляецца «сумяшчальнасць») - нармалізацыі сумяшчальнасці NFKC/NFKD з'яўляюцца іншым пытаннем; сумяшчальнасць (ці яго адсутнасць) для састарэлых кадовак што, напрыклад, былі асобныя знакі для грэцкага мю і «мікра» (гэта адно задавальненне, каб адкрыць, таму што «сумяшчальнасць» версія з'яўляецца той, які знаходзіцца ў блоку Latin 1)
дададзена аўтар Random832, крыніца

Калі два радкі Юнікода кананічна эквівалентныя струны сапраўды тое ж самае, толькі з выкарыстаннем розных паслядоўнасцяў Юнікода. Напрыклад, можа быць прадстаўлена альбо з дапамогай сімвала ці камбінацыі А і ◌̈.

Калі радкі толькі эквівалент сумяшчальнасці радок не абавязкова тое ж самае, але яны могуць быць аднолькавымі ў некаторых кантэкстах. напрыклад і далей можна лічыць такой жа, як сл.

Такім чынам, калі вы параўноўваеце радкі, вы павінны выкарыстоўваць кананічную эквівалентнасць, паколькі эквівалентнасць сумяшчальнасці не з'яўляецца рэальнай эквівалентнасці.

Але калі вы хочаце, каб адсартаваць набор радкоў можа мець сэнс выкарыстоўваць эквівалентнасць сумяшчальнасці як амаль ідэнтычныя.

5
дададзена

Гэта на самай справе даволі проста. UTF-8 на самай справе мае некалькі розных уяўленняў аднаго і таго ж «характар». (Я выкарыстоўваю знак у двукоссях, паколькі побайтно яны розныя, але практычна яны аднолькавыя). Прыклад прыведзены ў звязаным дакуменце.

Сімвал «C» можа быць прадстаўлены ў выглядзе паслядоўнасці байт 0xc387. Але яна таксама можа быць прадстаўлена ў выглядзе З (0x43), за якім варта паслядоўнасць байтаў 0x8ccca7. Такім чынам, вы можаце сказаць, што 0xc387 і 0x438ccca7 такія ж характар. Прычына, па якой працуе, з'яўляецца тое, што 0x8ccca7 з'яўляецца спалучэнне знака; гэта значыць ён прымае сімвал перад ім (а C тут), і змяняе яго.

Цяпер, наколькі розніца паміж кананічнай эквівалентнасці супраць эквівалентнасці сумяшчальнасці, мы павінны глядзець на персанажах ў цэлым.

Ёсць 2 віды персанажаў, тыя, якія перадаюць сэнс праз значэнне , і тыя, якія прымаюць іншы характар ​​і змяніць яго. Такім чынам, 9 з'яўляецца значным сімвалам. Супер-скрыпт ⁹ прымае гэта значэнне і змяняе яго ўяўленне. Так кананічна яны маюць розныя значэнні, але яны па-ранейшаму ўяўляюць сабой базавы характар.

Таму кананічная эквівалентнасць, дзе паслядоўнасць байт аказвае такі ж характар, з тым жа значэннем. Сумяшчальнасць эквівалентнасць, калі паслядоўнасць байт аказвае розны характар ​​з тым жа базавым значэннем (нават калі яно можа быць зменена). Такім чынам, 9 і ⁹ эквівалентныя сумяшчальнасці, так як яны абодва азначаюць «9», але не кананічна эквівалентныя, так як яны не маюць такое ж уяўленне ...

Надзея, што дапамагае ...

4
дададзена
@tchrist: Прачытайце адказ зноў. Я ніколі нават не згадаў аб розных спосабах прадстаўлення той жа кропка коды. Я сказаў, што ёсць некалькі спосабаў, якія прадстаўляюць той жа надрукаваны сімвал (з дапамогай камбінатар і некалькіх знакаў). Што тычыцца як UTF-8 і Unicode. Так што ваш downvote і каментар на самай справе не прэтэндуе на тое, што я сказаў. На самай справе, я ў асноўным рабіў тую ж кропку, што верхні плакат тут зрабіў (хоць і не так добра) ...
дададзена аўтар ircmaxell, крыніца

Ці кананічная эквівалентнасць або эквівалентнасць сумяшчальнасці больш актуальная для вас, залежыць ад вашага прыкладання. ASCII спосаб мыслення аб параўнанні радкоў прыкладна супастаўляецца кананічнай эквівалентнасці, але Unicode ўяўляе шмат моў. Я не думаю, што можна з упэўненасцю выказаць здагадку, што Unicode кадуе ўсе мовы такім чынам, што дазваляе разглядаць іх як і заходнееўрапейскай ASCII.

Figures 1 and 2 provide good examples of the two types of equivalence. Under compatibility equivalence, it looks like the same number in sub- and super- script form would compare equal. But I'm not sure that solve the same problem that as the cursive arabic form or the rotated characters.

Суровая праўда апрацоўкі тэксту Unicode з'яўляецца тое, што вы павінны глыбока пра патрабаванні апрацоўкі тэксту вашага прыкладання думаць, а потым звярнуцца да іх, а таксама, як вы можаце з дапамогай наяўных інструментаў. Гэта не непасрэдна на Ваша пытанне, але больш падрабязны адказ запатрабуе лінгвістычных экспертаў для кожнага з моў, якія вы чакаеце падтрымку.

4
дададзена

Праблема параўнаць радкі : два радкі, змест якіх з'яўляецца эквівалентам для мэт большасці прыкладанняў могуць утрымліваць адрозныя паслядоўнасці знакаў.

See Unicode's canonical equivalence: if the comparison algorithm is simple (or must be fast), the Unicode equivalence is not performed. This problem occurs, for instance, in xml canonical comparison, see http://www.w3.org/TR/xml-c14n

Каб пазбегнуць гэтай праблемы ... Які стандарт выкарыстоўваць? "Пашырыў UTF8" ці "кампактны UTF8"?
Выкарыстоўвайце «З» або «з + ◌̧.»?

W3C і іншыя (напр., Імёны файлаў ) прапануюць выкарыстоўваць «які складаецца кананічным» (прыняць да ўвагі З «найбольш кампактны »кароткія радкі) ... Так што,

The standard is C! in doubt use NFC

Для сумяшчальнасці, і «канвенцыі па канфігурацыі» выбар , рэкамендацыя з'яўляецца выкарыстанне <моцнага > NFC , каб "кананізаваць" знешнія радкі. Для захавання кананічнага XML, напрыклад, захоўваць яго ў «FORM_C». W3C з CSV ў Інтэрнэце Рабочай групы таксама рэкамендуем NFC (раздел 7.2).

PS: дэ "FORM_C" з'яўляецца форма па змаўчанні у большасці бібліятэк. Ex. ў РНР normalizer.isnormalized() .


Ther term "compostion form" (FORM_C) is used to both, to say that "a string is in the C-canonical form" (the result of a NFC transformation) and to say that a transforming algorithm is used... See http://www.macchiato.com/unicode/nfc-faq

<Р> (...) кожнай з наступных паслядоўнасцяў (першыя два з'яўляюцца паслядоўнасці з аднаго знака) уяўляюць сабой адзін і той жа характар:      <Ол>   <Літый> U + 00C5 (Å), лацінская загалоўная літара А з кольцам вышэйзгаданыя   <Літый> U + 212B (Å) Ангстрэм ЗНАК   <Літый> U + 0041 (А) ЛАЦІНСКАЙ СТАЛІЦА ЛІСТ А + U + 030A (̊) камбінаванне КАЛЬЦО ВЫШЭЙ         <Р> Гэтыя паслядоўнасці называюцца кананічна эквівалентнымі. Першы з гэтых формаў называецца NFC - для нармалізацыі формы С, дзе С з'яўляецца для кампазіцыя .   (...) Функцыя пераўтварэнні радкі S ў форме NFC можа быць скарочана як toNFC (S) , у той час як той, які правярае, ці з'яўляецца S ў NFC скарочана isNFC (S), .


Заўвага: для тэсту нармалізацыі маленькіх радкоў (чыстыя UTF-8 ці XML-аб'ектных спасылак), вы можаце выкарыстоўваць гэты тэст/нармалізуюць онлайн канвэртар .

1
дададзена
Прывітанне @userfuser магчыма, вам трэба месца, пра ўжыванне: у <я> параўнаць або <я> стандартаваць тэкст? Мой пост тут ідзе толькі пра «стандартаваць» прыкладання. PS: калі ўвесь свет выкарыстанне стандартна, параўнанне праблема знікае.
дададзена аўтар Peter Krauss, крыніца
Я заблытаўся. Я пайшоў у гэты інтэрнэт-старонцы тэставання і я ўвайду туды: «Тост калі ласка.» і паспрабаваць усе 4 Падарыў нормировок - ніхто не мяняе свой тэкст у любым выпадку, добра, за выключэннем таго, што яна змяняе коды, якія выкарыстоўваюцца для прадстаўлення гэтых знакаў. Ці магу я памылкова думаць, што «нармалізацыя» азначае «выдаліць усе дыякрытычны і падобнае», і гэта на самай справе азначае - проста зьмяніць кадыроўку UTF кадавання пад?
дададзена аўтар userfuser, крыніца