这是一个基础问题,但是我发现知道的人还真不多,在项目组里遇到的,事情是这样的:
前几天我写了一段从Server端下载图片到本地终端的代码,通过数据流的监控来看,下载下来的确实是和服务器上的图片大小一样,但是写在本地之后,貌似多了那么几个字节,而且图片打不开,把算法检查了好几遍都没有问题,由于服务器是在Ubuntu上搭建的,而客户端是在Windows上使用模拟器模拟的,于是怀疑是平台不同导致的,马上翻书,还真是这么回事!
首先,这个问题使用如下代码来测试:
#include
void CreateFile_A();
void CreateFile_B();
int main()
{
CreateFile_A();
CreateFile_B();
return 0;
}
void CreateFile_A()
{
FILE* fpa = fopen("a","w");
fprintf(fpa,"hello\n");
fclose(fpa);
}
void CreateFile_B()
{
FILE* fpb = fopen("b","wb");
fprintf(fpb,"hello\n");
fclose(fpb);
}
CreateFile_A()是以普通方式打开文件a并写入字符串,CreateFile_B()是以二进制方式打开文件b并写入字符串,以下截图为使用差分工具对文件以十六进制的形式进行比较的。
问题出来了,一个是7bit,一个是6bit,该代码运行在Win7下运行的。
如果这段代码在Linux下编译并运行,然后将a和b以十六进制的形式进行比较的话,如下图:
好吧~问题就在这里,OK,总结一下:
Windows平台下
如果以“文本”方式打开文件,当读取文件的时候,系统会将所有的"\r\n"转换成"\n";当写入文件的时候,系统会将"\n"转换成"\r\n"写入。
如果以"二进制"方式打开文件,则读/写都不会进行这样的转换。
Unix/Linux平台下,“文本”与“二进制”模式没有区别。
数据有字符型和非字符型(数)两种。按文本方式写文件指的是将数据转换为对应的字符型数据之后再写入文件。对于字符型数据,由于其本身就是ASCII码字符,一般不必转换,直接写入文件。但是,由于不同的系统对于换行符('\n')有不同的处理(转换)方式,在有的系统(如Windows)下也会对 '\n' 作适当的转换。
对于非字符型数据,都要进行转换处理。例如:int m = 12; 以及 double f = 2.3;,分别按照 "%d"、"%lf" 方式将 m 和 f 写入文件的时候,写入的分别是 '1'、'2' 两个字符以及 '2'、'.'、'3' 等三个字符的ASCII码值。显然,如果按照二进制方式写的话,在文件中一般 m 要占 4 个字节、f 要占 8 个字节。
问题解决了,但是感觉很不爽,翻开《C Primer Plus》,仔细看了看,书中对这个问题的描述非常详尽,我勒个去~~~
图片可能看不清楚,可以点击图片看高清图,附件中有代码和图片,另外,推荐使用BeyondCompare工具进行比较。
本文由电子匠人原创,如需转载请注明出处,谢谢。
电子匠人 2014-3-24 19:39
用户1570367 2014-3-20 21:41
这些细节平时真的没注意