【问题标题】:wcout function does not print a french characterwcout 函数不打印法语字符
【发布时间】:2013-03-09 14:13:14
【问题描述】:

我正在使用 wcin 将单个字符存储在 wchar_t 中。然后我尝试使用 wcout 调用和法语字符 'é' 打印它:但我在控制台上看不到它。

我的编译器是 g++ 4.5.4,我的操作系统是 Ubuntu 12.10 64 位。

这是我的尝试(wideChars.cpp):

#include <iostream>

int main(){
    using namespace std;

    wchar_t aChar;
    cout << "Enter your char : ";
    wcin >> aChar;
    wcout << L"You entered " << aChar << L" .\n";

    return 0;
}

当我启动程序时:

$ ./wideChars 
Enter your char : é
You entered  .

那么,这段代码有什么问题?

【问题讨论】:

  • 您的终端设置为什么编码?
  • 您好,请问如何查看?问候
  • 我收回我的回答。我已经在我自己的 Xubuntu 安装中检查了这一点,我看到了同样的问题。无论出于何种原因,wcin 拒绝读取“é”字符并设置失败位。
  • 我认为这是一个编译器问题:因为我将第 7 行替换为 wcout

标签: g++ wchar-t c++


【解决方案1】:

首先,添加一些错误检查。测试wcin.good()在输入后返回什么,wcout.good()在“你输入”打印后返回什么?我怀疑其中一个会返回false

您的LANGLC_* 环境变量设置为什么?

然后尝试通过在main() 的顶部添加这个来解决这个问题:wcin.imbue(std::locale("")); wcout.imbue(std::locale(""));

我现在手头没有我的 Ubuntu,所以我在这里瞎了眼,主要是在猜测。

更新

如果上述建议没有帮助,请尝试构建这样的语言环境并改用imbue() 这个语言环境。

std::locale loc (
    std::locale (),
    new std::codecvt_byname<wchar_t, char, std::mbstate_t>("")));

更新 2

这对我有用。 关键是还要设置 C 语言环境。恕我直言,这是 GNU C++ 标准库实现中的一个错误。除非我弄错了,否则设置 std::locale::global(""); 也应该设置 C 库语言环境。

#include <iostream>
#include <locale>
#include <clocale>

#define DUMP(x) do { std::wcerr << #x ": " << x << "\n"; } while (0)

int main(){
    using namespace std;

    std::locale loc ("");
    std::locale::global (loc);
    DUMP(std::setlocale(LC_ALL, NULL));
    DUMP(std::setlocale(LC_ALL, ""));    
    wcin.imbue (loc);

    DUMP (wcin.good());
    wchar_t aChar = 0;
    wcin >> aChar;
    DUMP (wcin.good());
    DUMP ((int)aChar);
    wcout << L"You entered " << aChar << L" .\n";

    return 0;
}

更新 3

我很困惑,现在我无法再次重现它,并且设置 std::locale::global(loc); 似乎也可以在 C 语言环境中做正确的事情。

【讨论】:

  • 感谢您的回答:在输入之后,wcin.good() 返回我 0(所以,假),并且在最后一个输出之后:wout.good() 返回我 1(所以, 真的)。我的 LANG 环境变量设置为 fr_FR.UTF-8,并且“echo $LC_*”给了我“escapeChars escapeChars.cpp limits limits.cpp wideChars wideChars.cpp”。现在我将尝试您的下一个解决方案。我的源文件和可执行文件是wideChars.cpp 和wideChars。
  • 不幸的是,您的解决方案都没有帮助我。即使我已经使用 call loc(locale, new codecvt_bytename) 进行了本地化。我还包括了语言环境定义,并在 main() 中保留了指令“使用命名空间 std”。这是我最新的源文件:pastebin.com/ir56SKP0
  • @LaurentBERNABE:我已经用一个工作示例更新了答案。
  • 你是对的,设置 C++ 语言环境应该也设置 C 语言环境(至少,只要你指定的 C++ 语言环境有名称;否则,行为关于 C 语言环境是实现定义的)。自然,它不会以另一种方式工作。设置 C 语言环境对 C++ 语言环境没有影响。如果这是 GNU 中的一个错误,则可能值得提交。
  • @wilx 非常感谢。这解决了我的问题。但是,我没有设法解决与 wcout 相关的问题(尽管我已经调用了 wcout.imbue(loc)):输入给 wcout 的字符串中的 'é' 没有打印出来。无论如何,这应该是另一个话题。
猜你喜欢
  • 1970-01-01
  • 1970-01-01
  • 1970-01-01
  • 2020-01-20
  • 2020-02-25
  • 2018-07-04
  • 2018-08-11
  • 1970-01-01
  • 2020-11-05
相关资源
最近更新 更多