マクロツイーター

はてダから移行した記事の表示が崩れてますが、そのうちに直せればいいのに(えっ)

“普通のユニコード”は NFC なのか

日本人が「普通に使う Unicode 文字列」は NFC とか NFD とかの正規化形式になっているかを、調べてみることにする。

といっても、何が「普通に使う Unicode 文字列」かを決めないと話が始まらない。ここでは、

レガシーな文字コードで表されたテキスト文字列を(標準の方法で)Unicode に変換して得られた Unicode 文字列

を対象にする。つまり、

特定の文字コードからの(標準的な)変換の結果の Unicode 文字列は必ず特定の Unicode 正規化形式を満たすか

を調べることにする。例えば Latin-1 について考えると、以下のようになる。

  • Latin-1 の文字列を Unicode に(標準的に)変換した場合、U+0000〜U+00FF の範囲にある文字しか現れない。
  • この範囲の文字からなる Unicode 文字列は必ず NFC である。
  • しかし、そのような文字列は必ずしも NFD ではない。例えば、「à」(U+00E0 一文字)という文字列は NFD で表すと〈0061 0300〉となる。
  • 同様に、「²」(U+00B2)は「2」(U+0032)の互換異体字であるので、Latin-1 の文字列は必ずしも NFKC や NFKD ではない。

調査結果

変換元文字コードNFC?NFD?NFKC?NFKD?
ASCIIYesYesYesYes
Latin-1(ISO-8859-1)YesNoNoNo
Windows-1252YesNoNoNo
MacRomanYesNoNoNo
JIS X 0201YesYesNoNo
JIS X 0208NoNoNoNo
CP932(Windows_31J)NoNoNoNo
MacJapaneseNoNoNoNo

NFC でない文字

これを見ると、「普通の日本語の Unicode 文字列」は NFC に必ずしもならない。それは次の文字が存在するためである。

  • U+212B 〈Å〉 ANGSTROM SIGN
    • 212B (NFC)→ 00C5 (つまり単一正準分解をもつ)
    • JIS X 0208 の 2 区 82 点の文字がこれに対応する。CP932、MacJapanese もこれを引き継ぐ(0x81F0)。
  • CJK 互換漢字
    • 例: FA19〈神〉 (NFC)→ 795E
    • CP932 に含まれる“IBM 漢字”の一部がこれに該当する。

つまり、JIS X 0208 と MacJapanese に関しては、一文字だけが NFC でない。

NFD でない文字

ここでの調査範囲だと、以下の文字が含まれる。

  • U+212B 〈Å〉 ANGSTROM SIGN
    • 212B (NFD)→ 0041 030A
  • CJK 互換漢字
    • 例: FA19〈神〉 (NFD)→ 795E
  • U+2260 〈≠〉 NOT EQUAL TO
    • 2260 (NFD)→ 003D 0338
  • アクセント付のラテン文字キリル文字
    • 例: 00E0〈à〉 (NFD)→ 0061 0300
    • 例: 0439〈й〉 (NFD)→ 0438 0306
  • 濁点・半濁点付のひらがな・カタカナ
    • 例: 304C〈が〉 (NFD)→ 304B 3099
    • 例: 30DD〈ポ〉 (NFD)→ 30DB 309A
    • ちなみに、MacJapanese には〈ゔ〉(0x8868)や〈ヸ〉(0x886B)がある。

*1:JIS X 0208 だけで考えて全て No なので、1 バイト文字集合と混用した場合も同様である。