Композиция Unicode в javascript

Я ищу способ подсчета лигатур как отдельных единиц, когда они отображаются пользователю, например. https://www.compart.com/en/unicode/U+FEFB.

Когда этот символ набирается (наберите G на арабской клавиатуре), он вставляется в форме декомпозиции, то есть U+0644 U+0627.

Я могу разложить U+FEFB на

escape(String.fromCodePoint(0xFEFB).normalize("NFKD")) // '%u0644%u0627'

Есть ли способ составить U+0644 U+0627 в 0xFEFB?

Почему это работает?

escape(String.fromCodePoint(0x0644, 0x0627).normalize("NFKC"))

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


person psmn    schedule 14.11.2019    source источник
comment
символы -> лигатура не является функцией (в математическом смысле), потому что может быть несколько лигатур, разлагающихся на одни и те же символы. В вашем случае лям + алеф может быть изолированным (FEFB) или окончательным (FEFC), и композитор не может знать, что вам нужно.   -  person georg    schedule 15.11.2019
comment
@georg Большое спасибо, теперь это имеет для меня смысл.   -  person psmn    schedule 15.11.2019


Ответы (1)


Учитывая, что спецификация ES2019 требует, чтобы реализация :

Пусть ns будет строковым значением, которое является результатом нормализации S в форме нормализации, названной f, как указано в https://unicode.org/reports/tr15/.

и учитывая, что https://www.unicode.org/Public/12.1.0/ucd/NormalizationTest.txt описывает этот символ как

FEFB;FEFB;FEFB;0644 0627;0644 0627; # (ﻻ; ﻻ; ﻻ; لا; لا; ) ARABIC LIGATURE LAM WITH ALEF ISOLATED FORM

это уступчивое поведение. Видеть

# 1. The following invariants must be true for all conformant implementations
#
#    NFC
#      c2 ==  toNFC(c1) ==  toNFC(c2) ==  toNFC(c3)
#      c4 ==  toNFC(c4) ==  toNFC(c5)
#
#    NFD
#      c3 ==  toNFD(c1) ==  toNFD(c2) ==  toNFD(c3)
#      c5 ==  toNFD(c4) ==  toNFD(c5)
#
#    NFKC
#      c4 == toNFKC(c1) == toNFKC(c2) == toNFKC(c3) == toNFKC(c4) == toNFKC(c5)
#
#    NFKD
#      c5 == toNFKD(c1) == toNFKD(c2) == toNFKD(c3) == toNFKD(c4) == toNFKD(c5)

Никакая нормализация не преобразует форму c4 или c5 обратно в c1, или c2, или c3.

Так что, по моему мнению любителя юникода, не существует совместимого со стандартом способа нормализовать U+0644 U+0627 обратно в U+FEFB.

person zerkms    schedule 14.11.2019
comment
Спасибо большое, мне было лень и я не копал достаточно глубоко. Теперь есть смысл. - person psmn; 15.11.2019