宽字符串函数

只要把字符串函数的 str 替换为 wcs (wide character string)就是对应的宽字符的函数

  1. char mbs[] = "你好";
  2. wchar_t wcs[10];
  3. mbstowcs(wcs, mbs, 10);
  1. #include<locale.h>
  2. setlocale(LC_ALL,"zh_CN.utf8");

mbstowcs 中的文件编码是根据 setlocale 设置的,而不是根据项目设置的

宽字符串

  1. whar_t *wsc = L"你好";
  • 字面量涉及到中文是和文件编码关联的,如上面代码
  • 转换过程中涉及到的中文是和 setlocale 关联的

locael

  1. char* setlocale (int category, const char* locale);

category:用于指定设置影响的范围,LC_CTYP E影响字符分类和字符转换,LC_TIME影响日期和时间的格式,LC_ALL影响所有内容。

不同编译器的第二个参数不一样,最好打印出返回值看看是否成功。

locael 影响的是 mbstowcs 函数对于窄字符串编码的读取

编译器编码

注意在 ide 里面设置的编码格式只是文件编码,没有设置编译器怎么解码 -DCMAKE_C_FLAGS=”/utf-8” 在编译器里设置上面就可以通知编译器怎么解码

wprintf

wprintf 会把参数宽字符串转成窄字符,然后打印到控制台。这个转换的过程需要知道目标窄字符的编码(宽字符的编码时确定的,一般就是 UTF-16),这个编码取决于 locale 。msvc 默认的 locale 是 C,因此打印时转换的结果并不会是 gbk 编码。如果你在 msvc 上打印之前调用 setlocal(LC_ALL, “chs”) ,结果就可以正确输出了。

三种编码格式

  • 文件编码,ide 右下角设置

  • 编译器编码,CMAKE 设置

  • locale,程序运行时的编码

由于文件编码和编译器编码在涉及到汉字时一定是一致的,不一致会破坏语法结构,所以 char mbs[] = "你好"; mbs 存储的是文件编码,mbstowcs(wcs, mbs, 10); 从 mbs 读取时就会根据编译器编码

控制台的编码格式

  1. #include <stdio.h>
  2. int main() {
  3. printf("哈哈哈");
  4. return 0;
  5. }

此时控制台会将 哈哈哈 对应的文件编码输出到屏幕上,很多时候控制台还是会乱码,需要将控制台的编码转换为文件编码。使用 chcp 命令来变换控制台编码。