Unicode正規化 その3

結合文字列は様々な問題を引き起こします。本来は、問題が起こらないようにOSやソフトウェアの側が対応するべきですが、現状ではUnicodeの急進的な規格に技術がそこまで追いついていません。ですから、私たちは自分でなんとかするしかなく、その手段が「単一コードの1文字」への変換なのです。

「単一コードの1文字」に変換する

「変換」と言うと、なにかとても難しい処理をするような印象をうけますよね。例えば、ある一定の数量的な法則に従ってバイナリコードを加工する、みたいな感じです。しかし、結合文字列を単一コードにする場合、この方法は使えません。そこには「一定の数量的な法則」がなく、あるのは言語の恣意性そのものだからです。

とは言うものの、やはり記号を扱うコンピュータ上の無機的な規格なので、Unicode Consortium は「結合文字列」と「単一コード1文字」の対応関係、いわばこの恣意的な関係を、属性のひとつとして各文字毎に逐一明記しています。

UnicodeData.txt

このファイルには各文字の属性が列挙されていて、その中に私たちが知りたい対応関係が書かれています。ここから「ポ」の文字を見てみましょう。

 30DD;KATAKANA LETTER PO;......;30DB 309A;......

カタカナ「ポ」は
 単一コードで「30DD
 結合文字列で「30DB 309A
であることが書かれています。

これから分かることは、ここに書かれている情報に従って、例えば「30DB 309A」を「30DD」に置換することで、私たちの目的である「単一コード1文字への変換」が実現できそうだということです。そして、この UnicodeData.txt の記述に従って置換することが、まさに「Unicode正規化」です。

Unicode正規化

「正規化」とはコンピュータ関連の技術用語で、「ある一定のルールに統一した一貫性のあるデータにする」というような意味です。その方法はデータの使用目的によって様々です。

DTPで例えると、私たちはよくテキストデータを加工して、数字やアルファベットをすべて半角にしたり、約物をすべて全角にしたりします。「一定のルールに統一した一貫性のあるデータ」にしているので、この加工も正規化のひとつであるといえます。

Unicode正規化は、UnicodeData.txt に記されている属性のひとつである「分解マッピング」を一定のルールにして、テキストを正規化することです。この点は非常に重要なことですので、ほんの少しだけ、詳しく見て行くことにします。

ここで、専門用語を3つ覚えてください。

「合成」「分解」「分解マッピング」

私はこれまで「結合文字列を単一コードの1文字にする」と長たらしく繰り返し書いてきましたが、Unicodeではこれを単純に「合成 Composition」といっています。言葉として「結合」に似ていて、紛らわしいのが難点です。
  結合 = バラバラなものがぴったりくっついて並んでいる感じ
  合成 = 化学変化のようにひとつに融合した感じ
私はこのようにイメージして、混乱しないようになんとか踏ん張っています。

一方、この「合成」とは逆のこと、つまり「単一コード1文字をバラバラにして結合文字列にする」ことを、これも単純に「分解 Decomposition」といいます。

そして、UnicodeData.txt で個々の文字に記されている「単一コード1文字と結合文字列の対応関係」を「分解マッピング Character Decomposition Mapping」といいます。当然、「あ」のようにこれ以上バラバラにできない文字は、分解マッピングになにも書かれていません。

「分解」は、文字をバラバラにするイメージそのままなので一見分かりやすそうですが、実は特殊な意味を示すかなり要注意な専門用語です。

神の異体字 左の文字は「神」の異体字です。分解マッピングを見てみます。

FA19;CJK COMPATIBILITY IDEOGRAPH-FA19;......;795E;......

単一コードは「FA19」、そしてなんと、この文字はこれ以上バラバラにはできないのに、分解マッピングで「795E」となっています。795E は「神」です。つまり、異体字「FA19」は、分解されると別の1文字になるのです。

どうしてそうなのかは後述しますが、「分解」という用語は1文字をバラバラにして結合文字列にするだけでなく、別の1文字にする意味でも使われるということを知っておいてください。

さて、専門用語がたくさん出てきましたので、ここで図にまとめてみます。

Unicode用語

他の用語もいくつか追加したいところなのですが、我慢してこれだけにしておきます。

次回はさらにUnicode正規化を見て行きます。

補注
「単一コード1文字」の用語である「合成済み文字」は使わないのかと、不思議に思われている方に向けて書いておきます。

合成済み文字 Precomposed Character」は、たしかに一般的に使われている用語ですが、私がはじめてそれを目にした時、かなり強い抵抗を感じてしまいました。Unicodeの文脈では、建前上、結合文字列の方が先である「結合文字列の方がUnicodeの規格にふさわしい形態であり、音声記号を伴う単一1文字は互換性のためやむなく定義されている」ということなのでしょうが、それは普通の感覚では受け入れがたいものです。Unicodeに知悉していない状態では、この用語で唐突に時系列が逆転することになり、ひどい混乱に陥ります。それを避けるために、あえて使うことを回避しました。

内心では、もっと分かりやすい「分解可能な文字 Decomposable Character」か「合成文字 Composite Character」を使いたかったのですが、「分解可能な文字」は用語としてそれほど一般的ではないこと、そして「合成文字」は逆の「結合文字列」としての意味で使っている人がかなりいることから、使用を断念しました。