ICode9

精准搜索请尝试: 精确搜索
首页 > 编程语言> 文章详细

如何解决c++文件读写流无法读取中文的问题(vc6.0)

2021-07-04 20:33:51  阅读:243  来源: 互联网

标签:编码 中文 字节 vc6.0 字符 读写 c++ 汉字 buf


代码

#include <iostream>
#include <fstream>
#include <locale>

using namespace std;

int main()
{
	setlocale(LC_ALL, "chs");	// 设置字符编码环境
	char buf;
	int x;
	wchar_t y, temp;
	ifstream is("D:\\存档\\OneDrive\\桌面\\作业\\测试文档.docx", ios::in);
	while(is.eof() == false)
	{

		is.read(&buf,sizeof(buf));
		if(int(buf) < 0)
		{
			y = 0x0000;
			y = buf;	// 取第一个字节的后4位
			y <<= 6;	// 为下一个字节的六位准备空间 
			is.read(&buf,sizeof(buf));
			// 取第二个字节的后六位
			temp = buf;
			temp = temp & (63);	// 取出temp的后六位
			y |= temp;
			y <<= 6;	// 为下一个字节的六位准备空间
			is.read(&buf, sizeof(buf));
			temp = buf;
			temp = temp & (63);
			y |= temp;

			printf("%S", &y);
			continue;
		}
		else
		{
			y = buf;
			printf("%s", &y);
		}
	}
	cout << endl;
	is.close();

	return 0;
}

运行结果

在这里插入图片描述

原理解释

在解决这个问题之前,我们需要先熟悉一下utf-8编码,大多数人认为中文在utf-8编码
里只占两个字节,其实这么表述是有问题的,真正的utf-8编码中,中文占据三个字节,
只不过只有两个字节是用来表示是哪个汉字的而已,具体详见下面这位大佬的文章

大佬文章

在这里插入图片描述

从上面的文章和这张图可以知道,ascii 表里面有的字符用的是第一种一个字节的编码方式,
而汉字用的是第三种编码方式,所以如果文档中只包含字符和汉字这两种字符的话,只需要
分类处理这两种情况就行了,而从图中可以发现中文编码和其他字符的不同之处:
	其他编码(只包含ascii里的字符)的字节都是以0开头的
	中文编码的三个字节都是从1开始的
所以,先将一个字节的内容读出来,之后将这个字节强转成为有符号数 int 类型,那么就会
出现所有的中文字符都是负数,所有的非中文字符都是正数,所以,对于强转之后是正数的
情况,直接输出就可以了,对于强转之后是负数的情况,就读取三个字节,之后将1号字节的
后四位取出来,2号字节的后六位取出来,3号字节的后六位取出来,并且将这些取出来的
二进制位重新拼接成为一个16位的字符,之后输出的就是汉字了,如果想要将汉字重新写回
文档并且不发生乱码的话,只需要将是汉字的部分重新构造成上面图中的三个字节编码的格式
写回文档就可以了

另外

这份代码里面的第一行代码是用来设置字符编码环境的
wchar_t 是宽字符,占据16位二进制位,定义原型是 typedef short wchar_t;
sprintf(%S, ..) 中的大S是专门用来输出宽字符的输出格式,这个格式必须在设置完编码格式之后才有效
c++的移位运算是算数移位
10进制的63是 0011 1111,只是c++里面不允许直接使用二进制值,所以我将这串二进制转换成为了十进制

标签:编码,中文,字节,vc6.0,字符,读写,c++,汉字,buf
来源: https://blog.csdn.net/qq_45760401/article/details/118466400

本站声明: 1. iCode9 技术分享网(下文简称本站)提供的所有内容,仅供技术学习、探讨和分享;
2. 关于本站的所有留言、评论、转载及引用,纯属内容发起人的个人观点,与本站观点和立场无关;
3. 关于本站的所有言论和文字,纯属内容发起人的个人观点,与本站观点和立场无关;
4. 本站文章均是网友提供,不完全保证技术分享内容的完整性、准确性、时效性、风险性和版权归属;如您发现该文章侵犯了您的权益,可联系我们第一时间进行删除;
5. 本站为非盈利性的个人网站,所有内容不会用来进行牟利,也不会利用任何形式的广告来间接获益,纯粹是为了广大技术爱好者提供技术内容和技术思想的分享性交流网站。

专注分享技术,共同学习,共同进步。侵权联系[81616952@qq.com]

Copyright (C)ICode9.com, All Rights Reserved.

ICode9版权所有