1

私のシステム、かなり普通の Ubuntu 13.10 では、フランス語のアクセント付き文字「éèàçù...」は、LC_ 環境変数が en_US.UTF-8 に設定されていても、使用するツールによって常に正しく処理されます。特に、grep、cat などのコマンド ライン ユーティリティでは、常にこれらの文字を問題なく読み取り、出力します。

これらの発言にもかかわらず、このような小さなプログラム

int main() {
  printf("%c", getchar());
  return 0;
}

ユーザーが「é」を入力すると失敗します。

manページと多くのグーグルから、stdoutを閉じてから再度開く標準的な方法はありません。man fwide() から、stdout がバイト モードの場合、それを閉じて再度開く以外にワイド文字モードに渡すことはできません... したがって、getwchar() と wprintf() は使用できません。

cat、grep などのすべてのユーティリティがワイド文字を管理する方法を再実装しているとは信じられませんが、私の調査では、他に方法はありません。

問題があるのは私のシステムですか?すべてのユーティリティが完璧に機能するため、方法がわかりません。何が欠けていますか?

4

3 に答える 3

3

C プログラムの開始時、stdoutstdinおよびstderrは、バイト指向でもワイド文字指向でもありません。 fwide(stdin, 0)この時点で 0 を返す必要があります。

最小限のプログラムを次のように拡張すると:

#include <stdio.h>
#include <locale.h>
#include <wchar.h>

int main()
{
        setlocale(LC_ALL, "");
        printf("%lc\n", getwchar());
        return 0;
}

その後、期待どおりに動作するはずです。(ここでの向きを明示的に設定する必要はありませんstdin。最初の操作はワイド文字操作であるため、ワイド文字の向きになります)。

ただし、ワイド文字を読みたい場合は代わりに使用する必要がありますgetwchar()getchar()

于 2013-11-13T13:59:05.720 に答える
0

UTF-8 文字は、文字ではなくバイト コードと見なされ、ASCII 以外の文字は 1 バイトを超えます。 この質問をチェック

詳細については

于 2013-11-13T13:49:18.423 に答える
0

あなたが言及するユーティリティは、一般的に行指向です。fgets()1 文字ではなく、eg を使用して行全体を読み取ろうとする場合も、うまくいくと思います。

単一の文字 (単なるバイトかもしれませんが、多くの場合そうです) を読み始めると、もちろん、エンコードの問題に非常に影響を受けやすくなります。

行終端エンコーディングが誤解されない限り (UTF-8 の場合は誤解されない)、行全体を読み取ることは問題なく機能します。

于 2013-11-13T13:49:29.630 に答える