编程文汇

c++跨平台处理utf字符串(续篇)

上一篇只是进行了探讨,并未做出结论。因为当时我也不知道那种方式最合适,这次给出我的结论吧。
不一定是最佳方案,但是简单,可行。不需要额外库,标准库即可
c++11应该就行了,我自己用的c++17。

本来不打算在c++处理字符串,后来发现还是处理更方便,这里记录一下处理方式:
只采用两种编码:ucs2,u8。ucs2用来做字符串处理,算是内部编码, u8做数据传输 、数据交换,算是外部编码。

所以只需要做ucs2<->utf8的转换,都是库函数。
u16string的操作也都是库函数。

  1. 字符串处理使用std::u16string。
  2. 字符串编码使用ucs2,支持6万字符吧,因为只在本机处理字符串,不在乎大端小端(标准库默认大端)。
  3. 字符串存储、网络发送都采用utf8
  4. 接收文本,只接受utf8编码。
using ucs2conv_t = std::wstring_convert<std::codecvt_utf8<char16_t>, char16_t>;
std::u16string u8toucs2(const std::string &u8str)
{
  ucs2conv_t ucs2conv;
  return ucs2conv.from_bytes(u8str);
}
std::string ucs2to8(const std::u16string &u16str)
{
  ucs2conv_t ucs2conv;
  return ucs2conv.to_bytes(u16str);
}
  1. 控制台打印采用utf8,在我win10开发机上没问题。linux上还没试,应该有类似方法。
#ifdef _WIN32
    SetConsoleOutputCP(CP_UTF8);
    SetConsoleCP(CP_UTF8);
#endif
std::string str = u8"发生的发";
std::cout<<str;

注:如果想要处理所有字符,不打算损失字符,把ucs2改成u32,u16string换成u32string即可。其余处理逻辑不变。