首先,我们需要有的概念是乱码的问题是由编码和解码方式引起的。涉及到编码方式的地方有3个:
源码字符集
执行字符集
运行环境字符集
源码字符集(the source character set):源码文件时使用何种编码格式保存的。
执行字符集(the execution character):可执行程序内保存的是何种编码(程序执行时内存中字符串编码)
源码字符集确切的说是编译器认为源码文件的编码方式,执行字符集是可执行程序采用的编码方式,而运行环境字符集则是环境支持的编码方式。编译程序处理字符串的过程,实际上是首先读入字符的二进制数,根据编码格式到另一种编码格式转换策略得到另外一串二进制数,所以1->2可能有二进制数的变化,而3则是通过既定的编码方式来解读2中的二进制数为字符(这里为什么说可能呢,因为1和2如果是相同的编码是不需要变化的)。
那么具体是哪些地方引起错误呢?在解答之前先介绍理解该问题的先验知识(由于我的运行环境是window简体中文版,所以以下的locale编码就是指GBK编码):
msvc2013编译程序时,处理源码字符集时,有BOM标识符的则正确识别(实际上目前就是有无BOM的utf-8),无BOM则使用本地Locale字符集(随系统设置而变),执行字符集默认用本地Locale字符集(其他msvc版本在看完本文甚至可以根据自己实验猜测处理)。
gcc编译程序时,默认两者都是uft-8,有finput-charset源码字符集和fexec-charset执行字符集则按照设置
qt 文本编辑器里设置的是源码字符集 ubuntu 系统默认为不带BOM的utf-8
在头文件中加入#pragma execution_character_set(“utf-8”) 使得源码字符集和执行字符集一致