East Asian Ambiguous Character Width の確認を ICU4C で行う
特にターミナル上で作業するにあたり、East Asian Ambiguous Character Width 問題は頭がいたい。
■とα、きれいに表示されているだろ。ウソみたいだろ。全角なんだぜ、それで・・・*1
という訳で、文字種によって、East Asian Ambiguous Character Width の属性を取得するコードを C で書いて確認してみました。
East Asian Ambiguous Character Width には、以下の属性があります。
定義 | 意味 |
---|---|
U_EA_NARROW | 半角 |
U_EA_WIDE | 全角 |
U_EA_HALFWIDTH | 半角で表す |
U_EA_FULLWIDTH | 全角で表す |
U_EA_AMBIGUOUS | 文脈に依存 |
U_EA_NEUTRAL | 上記以外(東アジア言語の文字ではない) |
属性の説明は、以下がわかりやすいです。
以下、確認コードです。ICU のダウンロード、ビルドから行うようになっていますが、環境に合わせて適宣省略・修正してください。
$ wget -c http://download.icu-project.org/files/icu4c/52.1/icu4c-52_1-src.tgz $ tar xfv icu4c-52_1-src.tgz $ cd icu/source $ ./configure $ make $ make check
上記のように ICU をダウンロード、ビルドします。
#include <unicode/uchar.h> #include <stdio.h> void test(UChar32 uc) { char *name; UEastAsianWidth eaw = (UEastAsianWidth) u_getIntPropertyValue(uc, UCHAR_EAST_ASIAN_WIDTH); printf("%04x ", uc); switch (eaw) { case U_EA_WIDE: name = "U_EA_WIDE"; break; case U_EA_FULLWIDTH: name = "U_EA_FULLWIDTH"; break; case U_EA_NARROW: name = "U_EA_NARROW"; break; case U_EA_NEUTRAL: name = "U_EA_NEUTRAL"; break; case U_EA_HALFWIDTH: name = "U_EA_HALFWIDTH"; break; case U_EA_AMBIGUOUS: name = "U_EA_AMBIGUOUS"; break; default: name = "default"; break; } printf("%s\n", name); } int main() { test(L'A'); test(L'あ'); test(L'〜'); test(L'ア'); test(L'■'); test(L'α'); return 0; }
上記のようなソースコードを、以下の Makefile でビルド・実行します。
all: gcc AmbiguousTest.c -Iicu/source/common -Licu/source/lib -licuuc -licudata run: LD_LIBRARY_PATH=icu/source/lib ./a.out clean: rm -f a.out
結果は以下のとおりです。
$ make $ make run 0041 U_EA_NARROW 3042 U_EA_WIDE ff5e U_EA_FULLWIDTH ff71 U_EA_HALFWIDTH 25a0 U_EA_AMBIGUOUS 03b1 U_EA_AMBIGUOUS
これで ■とαが U_EA_AMBIGUOUS で取得できています。