【问题标题】:Does std::wstring support UTF-16 and UTF-32 on Windows?std::wstring 在 Windows 上是否支持 UTF-16 和 UTF-32?
【发布时间】:2014-11-14 07:28:30
【问题描述】:

我正在学习 Unicode,有几个问题希望得到解答。

1) 我在 Linux 上读过,std::wstring 是 4 字节,而在 Windows 上是 2 字节。这是否意味着 Linux 内部支持是 UTF-32 而 Windows 是 UTF-16

2) std::wstring 的使用和std::string 接口的使用很相似吗?

3) VC++ 是否支持使用 4 字节 std::wstring?

4) 如果使用 std::wstring 是否需要更改编译器选项?

作为旁注,我遇到了一个使用 UTF-8 的字符串库,它具有与 std::string 非常相似的接口,它提供了熟悉的功能,例如长度、子字符串、查找、大写/小写转换等。库是 Glib::ustring

请随时添加任何 cmets 或其他建议,因为我真的需要它。

谢谢!

【问题讨论】:

  • C++11 char32_t 类型应该提供一个解决方案,但是它在微软的待办事项列表中是最后一个。非常怀疑它在未来 10 年内是否会派上用场 :) 是的,你几乎总是需要一个库来做任何不平凡的事情。 ICU是一种常见的选择。
  • @HansPassant,这让我对 VC++ 对未声明的标识符等感到困惑。 ICU 太大了……我想我要试试 Glib::ustring 看看它是否能满足我的所有需求。顺便说一句,不久前你警告过我关于代码页的事情,你是对的。
  • 关于它的几乎所有内容都写在 utf8everywhere.org 宣言中。

标签: c++ unicode utf-8 utf-16 utf-32


【解决方案1】:

1) wstringbasic_string<wchar_t>wchar_t 的大小取决于实现并且与编码无关(标准只是说“它的值可以代表最大扩展字符的所有成员的不同代码在支持的语言环境中指定的集合”。但是,有sizeof(wchar_t)=4字节的实现支持UTF-32,sizeof(wchar_t)=2字节支持UTF-16。

2) wstringbasic_string<wchar_t>stringbasic_string<char>,所以是的,这是一个非常相似的界面。不过,您将不得不使用wcoutwcinwfstream,并且还有其他一些类似的约束条件。

3) 不,MSVC 将wchar_t 定义为unsigned short,正如您所说,它定义并限制了wstring。 MSVC 提供了将wchar_t 处理为 typedef 而不是内部类型的可能性。你可以想象然后重新定义 typedef,但我怀疑这是非常危险和邪恶的。

4) 不,您可以选择所需的字符串类型。

5) UTF-32 和标准:有趣的是,在与编码无关的 C++ 标准中,仅针对 codecvt 明确提及 UTF-32:“专业化 codecvt <char32_t, char, mbstate_t> 在 UTF-32 之间转换和 UTF-8 编码形式。codecvt 在窄字符和宽字符的本机字符集之间转换。“这表明char32_t 将是 UTF-32 的可移植方法。不幸的是 MSVC 还不支持这种类型。

【讨论】:

  • Christophe 和@RemyLebeau,感谢您的出色回答。
  • "MSVC 将 wchar_t 定义为 unsigned short" 默认情况下,wchar_t 是内置类型。您链接到的页面解释了这一点。
  • @DDrmmr,是的,我的措辞具有误导性。当然,使用编译器的默认选项,MSVC 将 wchar_t 处理为本机类型。我的意思是 MSVC 的实施——无论选项如何——为这种类型提供了与无符号短路相同的特征/限制。
【解决方案2】:

1) 我在 Linux 上读过,std::wstring 是 4 字节,而在 Windows 上,它是 2 字节。这是否意味着 Linux 内部支持是 UTF-32 而 Windows 是 UTF-16?

实际上是wchar_t,而不是std::wstring,在Linux 上是4 个字节,在Windows 上是2 个字节。 std::wstringstd::basic_string<wchar_t> 的 typedef,所以std::wstring 在 Linux 上支持 UTF-32,在 Windows 上支持 UTF-16,是的。

2) std::wstring 的使用和std::string 接口的使用很相似吗?

std::wstringstd::string 都是 std:basic_string 的 typedef,因此它们具有相同的接口,只是 value_type 类型不同(分别为wchar_tchar)。

3) VC++ 是否支持使用 4 字节 std::wstring?

不适用于std::wstring 本身,不。但是你可以创建自己的std::basic_string typedef,例如:

typedef std::basic_string<int32_t> u32string;

事实上,这正是新的 C++11 std::u16stringstd::u32string 类型的定义方式:

typedef std::basic_string<char16_t> u16string;
typedef std::basic_string<char32_t> u32string;

TCHAR 创建一个std::basic_string 的typedef 也并非闻所未闻:

typedef std::basic_string<TCHAR> tstring;

作为旁注,我遇到了一个使用 UTF-8 的字符串库,它具有与 std::string 非常相似的接口,它提供了熟悉的功能,例如长度、子字符串、查找、大写/小写转换等。库是 Glib::ustring。

从技术上讲,您可以(很多人都这样做)为 UTF-8 使用标准 std::stringGlib::ustring 只是通过使用 gunicharguint32 的 typedef)而不是 char 更进一步,并公开其接口以根据原始 Unicode 代码点而不是编码的代码单元进行操作。

【讨论】:

    猜你喜欢
    • 2020-03-22
    • 2011-05-13
    • 2011-11-01
    • 1970-01-01
    • 1970-01-01
    • 1970-01-01
    • 1970-01-01
    • 1970-01-01
    • 1970-01-01
    相关资源
    最近更新 更多