我尝试使用 wchar_t、char16_t 和 char32_t 类型打印汉字,但无济于事。

I'm trying to print a Chinese character using the types wchar_t, char16_t and char32_t, to no avail.

我正在尝试使用 wchar_tchar16_tchar32_t 类型打印汉字 ,但没有成功 (live example)

#include <iostream>
int main()
{
    char x[] = "中";            // Chinese character with unicode point U+4E2D
    char y[] = u8"中";
    wchar_t z = L'中';
    char16_t b = u'\u4e2d';
    char32_t a = U'\U00004e2d';

    std::cout << x << '\n';     // Ok
    std::cout << y << '\n';     // Ok
    std::wcout << z << '\n';    // ?? 
    std::cout << a << '\n';     // prints the decimal number (20013) corresponding to the unicode point U+4E2D
    std::cout << b << '\n';     //             "                    "                   "
}

由于您 运行 在 Linux 系统上进行测试,源代码是 UTF-8,这就是为什么 xy 是同一回事.这些字节被 std::cout << xstd::cout << y 分流到标准输出,当您查看网页时(或者当您查看 linux 终端时),您会看到字符如你所料。

如果你做了两件事,

std::wcout << z 将打印:

std::ios::sync_with_stdio(false);
std::wcout.imbue(std::locale("en_US.utf8"));

在不与 C 取消同步的情况下,GNU libstdc++ 通过 C IO 流,它永远无法在同一流上打印窄字符后打印宽字符。 LLVM libc++ 似乎甚至可以同步工作,但当然仍然需要 imbue 来告诉流如何将宽字符转换为它发送到标准输出的字节。

要打印 ba,您必须将它们转换为宽或窄;即使 wbuffer_convert 设置 char32_t 流也需要大量工作。它看起来像这样:

std::wstring_convert<std::codecvt_utf8<char32_t>, char32_t> conv32;
std::cout << conv32.to_bytes(a) << '\n';

综合起来:http://coliru.stacked-crooked.com/a/a809c38e21cc1743