WindowsのUnicode事情
- だいぶ前からOS内部は完全にUnicode化されている。
- OSの内部コードはUTF-
816リトルエンディアンらしい(https://ja.wikipedia.org/wiki/UTF-16) - 表面的にはシフトJISも使われている。ユーザーからはシフトJISが見えている。
- Unicode文字をワイド文字と呼ぶ、そうでない旧来からの文字はアンシ文字(ANSI)と言うらしい。shift_jisがANSIとはコレイカニ? だが、しょうがない。
- ワイド文字では16ビットが文字単位。実際のOS内部エンコーディングスキームはUTF-16LE。
- UTF-16ということは古いUCS-2とは違い、サロゲートペアを持つ。2007年の記事 http://codezine.jp/article/detail/1592 によると、既にWindows Vistaの時代からサロゲートペアが使われていた。
- 日本語文字で最初のサロゲートペア文字は U+2000B(そのグリフは http://glyphwiki.org/wiki/u2000b-ue0100)
- 辰吉丈一郎の「じょう」はこの文字(異体字?)らしい。
- もし「BMPのみ」ということであれば、UTF-16からサロゲートペアを除く必要がある。
- 内部はBOMなしのリトルエンディアンなので、ビッグエンディアンのときはバイト反転をする。
- 文字列のバイト列のなかでヌルバイトは頻繁に出てくるからCスタイルの文字列はどうにもならない。
- 16ビットのヌル(0のビットが16個)をターミネーターマーク使うテもあるが、長さをヘッダに持ったほうがいいかもしれない。
- バッファが固定長なら、残余はヌルバイトで埋めるのが安全。
- MicrosoftのC/C++のライブリは、「ASCIIとso-calledアンシ」と「ワイド文字」で別な名前の関数を持っている。printfならワイド文字版のwprintfとか。
- ワイド文字例型は、16bitのunsigned intへのポインタ型。アンシ文字列型は8bitのcharへのポインタ。ワイド文字へのポインタを使えば、終端でハマる問題はないが、安全ではない。
- バッファへのポインタではなくてオブジェクトを使うべきだろう。
- 文字列リテラルはchar *になるので注意。Lを付けるとwchar_t * になる。
- ソースコードのエンコーディングとの絡みがまためんどくさい。
- ANSIとかwchar(ワイド文字)とかの概念はWindows固有で他のプラットフォームへの可搬性はない。
- C++としての標準に wchar_t があるが、これはエンコーディングが決まってるわけじゃないから、実装依存の概念。