位域问题1:C/C++ code//环境是VC 6.0#includestdio.hstruct myStruct{unsigned char a :8unsigned char
位域 问题1:
C/C++ code
//环境是VC 6.0#include<stdio.h>struct myStruct{ unsigned char a :8; unsigned char b :1; unsigned char c :1; unsigned char d :1; unsigned short e :13; unsigned char f :2; unsigned char g :2; unsigned char h :4;}var_t;int main(){ printf("The size = %d\n",sizeof(struct myStruct)); return 0;}
结果是6 为什么是6??我觉得应该是5
问题2:
C/C++ code
struct myStruct{ int a :8; int b :1; int c :1; int d :1; int e :13; int f :2; int g :2; int h :4;}var_t;int main(){ printf("The size = %d\n",sizeof(struct myStruct)); return 0;}
结果为4 为什么是4呢?而换成下面却是6!!我觉得应该是5
C/C++ code
struct myStruct{ unsigned short a :8; unsigned short b :1; unsigned short c :1; unsigned short d :1; unsigned short e :13; unsigned short f :2; unsigned short g :2; unsigned short h :4;}var_t;int main(){ printf("The size = %d\n",sizeof(struct myStruct)); return 0;}
[解决办法] 一个位域必须存储在同一个字节中,不能跨两个字节。如一个字节所剩空间不够存放另一位域时,应从下一单元起存放该位域。也可以有意使某位域从下一单元开始 [解决办法] 位域成员不能单独被取sizeof值,我们这里要讨论的是含有位域的结构 体的sizeof,只是考虑到其特殊性而将其专门列了出来。 C99规定int、unsigned int和bool可以作为位域类型,但编译器几乎都对此作了扩展, 允许其它类型类型的存在。 使用位域的主要目的是压缩存储,其大致规则为: 1) 如果相邻位域字段的类型相同,且其位宽之和小于类型的sizeof大小,则后面的字 段将紧邻前一个字段存储,直到不能容纳为止; 2) 如果相邻位域字段的类型相同,但其位宽之和大于类型的sizeof大小,则后面的字 段将从新的存储单元开始,其偏移量为其类型大小的整数倍; 3) 如果相邻的位域字段的类型不同,则各编译器的具体实现有差异,VC6采取不压缩方 式,Dev-C++采取压缩方式; 4) 如果位域字段之间穿插着非位域字段,则不进行压缩; 5) 整个结构体的总大小为最宽基本类型成员大小的整数倍。 [解决办法] 同时 位域类型 要考虑字节对齐 [解决办法] 举例 struct myStruct { unsigned short a :8; unsigned short b :1; unsigned short c :1; unsigned short d :1; unsigned short e :13; unsigned short f :2; unsigned short g :2; unsigned short h :4; }var_t; a b c d两个字节 e f 两个字节 h本身两个字节(字节对齐) 所以 为6个字节 [解决办法] VC调试(TC或BC用TD调试)时按Alt+8、Alt+6和Alt+5,打开汇编窗口、内存窗口和寄存器窗口看每句C对应的汇编、单步执行并观察相应内存和寄存器变化,这样过一遍不就啥都明白了吗。 对VC来说,所谓‘调试时’就是编译连接通过以后,按F10或F11键单步执行一步以后的时候,或者在某行按F9设了断点后按F5执行停在该断点处的时候。 (Linux或Unix下可以在用GDB调试时,看每句C对应的汇编并单步执行观察相应内存和寄存器变化。)”
bit实际上就是把字节分开显示而已,其他和结构一样 struct myStruct { unsigned char a :8; unsigned char b :1; unsigned char c :1; unsigned char d :1; unsigned short e :13; unsigned char f :2; unsigned char g :2; unsigned char h :4; }var_t; 相当于 { unsigned char a; // unsigned char un1; //bcd short e; unsigned char un2; //fgh
} 一共5个字节,但最长的是short,按2字节对齐,是6
struct myStruct { int a :8; int b :1; int c :1; int d :1; int e :13; int f :2; int g :2; int h :4; }var_t;
一共32位,因此一个int就够了,所以是4 struct myStruct { unsigned short a :8; unsigned short b :1; unsigned short c :1; unsigned short d :1; unsigned short e :13; unsigned short f :2; unsigned short g :2; unsigned short h :4; }var_t; 相当于 { short un1;//abcd short un2; //ef short un3; //gh } 显然是6