1

我有一个c++11正在编写的库,它提供了一个用于设置环境变量的跨平台 API。的好处c++11是所有char字符串都是UTF-8

environment::Set(const std::string& name, const std::string& value)

在 Windows 上,SetEnvironmentVariable函数有两个别名SetEnvironmentVariableASetEnvironmentVariableW.

我的理解是,宽版本采用wchar_tWindows 领域的 16 位,UTF-16而 ANSI 版本是 ASCII。

std::string使用此函数将转换为UTF-16 (使用std::codecvt_utf8_utf16或其他内容)然后放入函数的宽版本的正确方法是否正确?

4

2 回答 2

4

c++11的好处是所有char字符串都是UTF-8:

这不是 C++11 为普通字符串文字指定的,你会发现 VC++ 并没有做到这一点。如果你想要 UTF-8 字符串,那么你必须自己确保。

我的理解是,宽版本采用 16 位 wchar_t,在 Windows 领域是 UTF-16,而 ANSI 版本是 ASCII。

这些*A函数始终使用系统代码页,它是 ASCII 的扩展版本(绝不是 UTF-8)。

使用此函数将 std::string 转换为 UTF-16(使用 std::codecvt_utf8_utf16 或其他内容)然后放入函数的宽版本的正确方法是什么?

如果您确保您的字符串是 UTF-8(这是一个好主意,IMO),那么转换为 UTF-16 并使用该wchar_t版本是正确的做法。

#include <Windows.h>
#include <codecvt>

int main() {
  std::wstring_convert<std::codecvt_utf8_utf16<wchar_t>,wchar_t> convert;

  std::string var = "\xD0\xBA\xD0\xBE\xD1\x88\xD0\xBA\xD0\xB0"; // кошка
  std::string val = "\xE6\x97\xA5\xE6\x9C\xAC\xE5\x9B\xBD";     // 日本国

  SetEnvironmentVariableW(convert.from_bytes(var).c_str(),
                          convert.from_bytes(val).c_str());
}

在完全符合 C++11 的情况下,我们可以编写std::string var = u8"кошка";,但是 VC++ 没有实现这一点,而且它似乎是一个非常低优先级的项目,因为它没有明确出现在他们的 C++14一致性路线图上。

或者,std::string var = "кошка";如果您将源代码保存为“没有 BOM 的 UTF-8”,则可以编写。请注意,该方法有一些警告,例如您不能使用 wchar_t 文字。

于 2013-09-25T15:37:21.450 回答
4

是的,Windows 仅通过其 API 的“宽”版本(使用 UTF-16)支持 Unicode;“ANSI”(char基于 - 的)函数仅支持“本地”代码页,而不支持 UTF-8。

于 2013-09-25T14:52:45.100 回答