记录一下从网上搜索的关于系统字节序的相关帖子内容
因为现行的计算机都是以八位一个字节为存储单位,那么一个16位的整数,也就是C语言中的short,在内存中可能有两种存储顺序big-endian和litte-endian. 考虑一个short整数0x3132(0x32是低位,0x31是高位),把它赋值给一个short变量,那么它在内存中的存储可能有如下两种情况:大端字节(Big-endian):----------------->>>>>>>>内存地址增大方向short变量地址 0x1000 0x1001_____________________________| || 0x31 | 0x32|________________ | ________________高位字节在低位字节的前面,也就是高位在内存地址低的一端.可以这样记住(大端->高位->在前->正常的逻辑顺序)小端字节(little-endian):----------------->>>>>>>>内存地址增大方向short变量地址 0x1000 0x1001_____________________________| || 0x32 | 0x31|________________ | ________________低位字节在高位字节的前面,也就是低位在内存地址低的一端.可以这样记住(小端->低位->在前->与正常逻辑顺序相反)可以做个实验在windows上下如下程序#include #include void main( void ){ short test; FILE* fp; test = 0x3132; //(31ASIIC码的’1’,32ASIIC码的’2’) if ((fp = fopen ("c://test.txt", "wb")) == NULL) assert(0); fwrite(&test, sizeof(short), 1, fp); fclose(fp);} 然后在C盘下打开test.txt文件,可以看见内容是21,而test等于0x3132,可以明显的看出来x86的字节顺序是低位在前.如果我们把这段同样的代码放到(big-endian)的机器上执行,那么打出来的文件就是12.这在本机中使用是没有问题的.但当你把这个文件从一个big- endian机器复制到一个little-endian机器上时就出现问题了.
下面代码示范了两种检测系统字节序的方法。第一种方法,使用强制类型转换的方式。C 语言在把占用2个字节的 short 变量强制转换为 char 之后,会把 short 变量的首地址赋给 char 变量,可以根据 char 变量的值判断系统字节序是 大端 还是 小端。第二种方法,利用 联合类型 的特性。联合类型 共享同一段内存,首地址是相同的。/******************* * 文件名:endian.c ******************/#include <stdio.h>
/********************************************************* * 使用类型的强制转换实现little-endian与big-endian的判断 ********************************************************* * 返回值: * 1 表示是小端字节序。 * 0 表示不是小端字节序。 *********************************************************/int is_little_endian_a(void){ unsigned short flag = 0x4321; if(*(unsigned char*)&flag == 0x21) return 1; else return 0;}
/********************************************************************************* * 利用联合的特点来判断little-endian与big-endian ********************************************************************************* * 返回值: * 1 表示是小端字节序。 * 0 表示是大端字节序。 * -1 表示不能使用这种方法确定字节序。比如有的机器的 short 长度不是 2 。 ********************************************************************************/int is_little_endian_b(void){ union endian_un{ short var; char bits[sizeof(short)]; };
union endian_un flag; flag.var=0x0102;
//判断低位和高位的存储内容,确定是何种方式 if(sizeof(short) == 2){ if(flag.bits[0] == 1 && flag.bits[1] == 2) return 0; else if(flag.bits[0] == 2 && flag.bits[1] == 1) return 1; else return -1; } return -1;}
int main(void){ int type = 0;
type = is_little_endian_a(); if (1 == type) printf("judged by first method, little-endian/n"); else if (0 == type) printf("judged by first method, big-endian/n");
type = is_little_endian_b(); if (1 == type) printf("judged by second method, little-endian/n"); else if (0 == type) printf("judged by second method, big-endian/n"); else printf("can't judge it/n");
return 0;}