1 移位(占内存,移植性一般)
2 强制转换(方便,移植性差)
3 宏定义(易读,移植性好)
#define ToByte(x, i) (((char*)(&x))[i])
x表示数据,i表示字节号
4 联合体
union
{
unsigned long dw;
struck
{
unsigned char b0;
unsigned char b1;
unsigned char b2;
unsigned char b3;
} byte;
} value;
访问时直接,方便,如value.dw,value.byte.b0等
5 联合体+宏定义
#define value value.dw
#define value_0 value.byte.b0
#define value_1 value.byte.b1
#define value_2 value.byte.b2
#define value_3 value.byte.b3
直观,使用方便
刚刚在讨论字节序的问题的时候出现了这么一个问题,怎么访问一个整型变量里面的各个字节,我们知道,如果要访问这个整型最低地址一个字节的数据的话,可以通过如下方式:
char a = *(char*)&整型变量名;
这里先将整型数通过取地址符号获得变量的开始的地址,为什么要(char*)进行强制类型转换呢,因为对于整型数据的话,表示的就是以首地址开始的4个字节,它是一个整体,取它的地址后,地址对应的类型为int*类型,即如果通过这个指针访问的话,只能访问到整个4个字节的空间的数据,没法访问单个字节。通过(char*)就将int*整型指针类型转换为字符型指针类型。这样就可以访问低地址这个字节的数据啦。那么如果我想访问第2个,第3个,第4个字节的数据呢。我们先来看看以下表示:
char * pc = (char*)&整型变量名;
pc现在指向首字节,要访问下个字节只需要*(p+1)就可以(即p[1]),同理下一个*(p+2)、*(p+3)(p[2]、p[3])。那如果我们不进行指针转换呢。我们看如下表示:
int * pi = &整型变量名;
这个时候用*pi将获得四个字节的内容。pi+1将指向下一个整型地址空间,即0x0005地址,所以*(pi+1)(即pi[1])将访问0x0005地址开始的四个字节的内容。这里有点需要强调的是,*(pi+i)总是等于pi[i]。整个过程如下图所示:
图一:指针加1的差别
通过上面的分析,想获得一个整型数里面的某个字节的值的话,我们可以如下表示:
char a = ((char*)&整型变量名)[i];
i=0表示首字节,1表示第2个字节,依次类推。