wifstreamを使用してテキストファイルをワイド文字列(std :: wstring)に読み取る場合、ストリーム実装はさまざまなエンコーディングをサポートしますか?つまり、ASCII、UTF-8、UTF-16ファイルなどの読み取りに使用できますか?
そうでない場合、私は何をしなければなりませんか?
(違いが生じる場合は、ファイル全体を読み取る必要があります)
wifstreamを使用してテキストファイルをワイド文字列(std :: wstring)に読み取る場合、ストリーム実装はさまざまなエンコーディングをサポートしますか?つまり、ASCII、UTF-8、UTF-16ファイルなどの読み取りに使用できますか?
そうでない場合、私は何をしなければなりませんか?
(違いが生じる場合は、ファイル全体を読み取る必要があります)
C ++は、std::locale
およびファセットによる文字エンコードをサポートしstd::codecvt
ます。一般的な考え方は、locale
オブジェクトは、文化ごとに、(人間の)言語ごとに異なる可能性のあるシステムの側面を記述するというものです。facet
これらの側面は、ローカリゼーションに依存するオブジェクト(I / Oストリームを含む)の構築方法を定義するテンプレート引数であるsに分解されます。からの読み取りistream
またはへの書き込みを行うostream
場合、各文字の実際の書き込みは、ロケールのファセットによってフィルタリングされます。ファセットは、Unicodeタイプのエンコードだけでなく、大きな数値の書き込み方法(コンマやピリオドなど)、通貨、時間、大文字と小文字、およびその他の多くの詳細などのさまざまな機能をカバーします。
ただし、エンコーディングを実行する機能が存在するからといって、標準ライブラリが実際にすべてのエンコーディングを処理するわけではなく、そのようなコードを簡単に正しく実行できるわけでもありません。読み取る必要のある文字のサイズ(エンコード部分は言うまでもなく)などの基本的なものでさえ、wchar_t
小さすぎる(データをマングリングする)、または大きすぎる(スペースを浪費する)可能性があるため、最も一般的なコンパイラー(例: VisualC++とGnuC++)は、実装の大きさが異なります。したがって、通常、実際のエンコーディングを行うには外部ライブラリを見つける必要があります。
すべてのベースをカバーする私が見つけることができる最も簡単な例は、BoostのUTF-8 codecvtファセットからのものであり、IOストリームで使用するためにUTF-8(UCS4)を具体的にエンコードしようとする例があります。そのままコピーすることはお勧めしませんが、このように見えます。それを理解するには、ソースをもう少し掘り下げる必要があります(そして私は主張しません):
typedef wchar_t ucs4_t;
std::locale old_locale;
std::locale utf8_locale(old_locale,new utf8_codecvt_facet<ucs4_t>);
...
std::wifstream input_file("data.utf8");
input_file.imbue(utf8_locale);
ucs4_t item = 0;
while (ifs >> item) { ... }
ロケール、およびロケールがファセット(を含む)をどのように使用するかについて詳しく理解するcodecvt
には、以下を参照してください。
ifstream
ファイルのエンコードは気にしません。ファイルからchars(bytes)を読み取るだけです。wifstream
wide bytes(wchar_t
)を読み取りますが、それでもファイルのエンコードについては何も知りません。wifstream
UCS-2には十分です— Unicode用の固定長文字エンコード(各文字は2バイトで表されます)。
IBM ICUライブラリーを使用して、Unicodeファイルを処理できます。
International Component for Unicode(ICU)は、Unicodeサポート、ソフトウェア国際化(I18N)、およびグローバリゼーション(G11N)用の成熟したポータブルC / C ++およびJavaライブラリのセットであり、すべてのプラットフォームで同じ結果をアプリケーションに提供します。
ICUは、商用ソフトウェアと他のオープンソースまたはフリーソフトウェアの両方での使用に適した非制限的なオープンソースライセンスの下でリリースされています。
ワイド文字列とワイド文字ストリームの設計は、UTF-8、UTF-16、およびUnicodeよりも前のものです。技術を習得したい場合、標準文字列と標準ストリームは必ずしもASCIIで動作するとは限りません(基本的にすべてのコンピューターがASCIIを使用しているだけです。EBCDICマシンを使用している可能性があります)。
Raymond Chenはかつて、さまざまなワイド文字ストリーム/文字列タイプを操作する方法を示すシリーズを作成しました。