C/C++中的位域在百度百科里面介绍了一些基础知识,但遗憾的是没有和内存示意相结合,初学者容易理解偏差。
以下内容是假设读者已初步理解掌握了百度百科“位域”的基础上,再加以补充说明:《Soloe@csdn,转载请说明》
1、位域中的变量字段,最小占用是其变量说明的类型在“正常占用”下的大小。
什么意思呢,看下面这个例子:
struct A
{
int a:5;
int b:3;
};
这里a和b总共占用了8bit,那么这个结构体的大小是否为1字节?
答案是no,笔者电脑上 sizeof(A) 结果为4,这是因为在x86下int占4个字节。
2、继续前面的案例,a和b在这四个字节中处于哪个位置?
高位 低位
高位 | 低位 | ||
---|---|---|---|
00000100 | 00000011 | 00000001 | 00000000 |
bbbaaaaaa |
答案如上图所示,a占了最低位的5个bit,b占了a左边的3个比特
3、从结构体位域转换成正常变量,需要注意哪些事项:
看下面的例子:
#include <iostream>
#include <memory.h>
using namespace std;
struct A
{
int a:5;
int b:3;
};
int main(void)
{
char str[100] = "0134324324afsadfsdlfjlsdjfl";
struct A d;
memcpy(&d, str, sizeof(A));
cout << d.a << endl;
cout << d.b << endl;
return 0;
}
输出是多少?
答案是:
-16
1
原因是int a和int b是有符号数,要注意符号位的扩展。
高位 | 低位 | ||
---|---|---|---|
00000100 | 00000011 | 00000001 | 00000000 |
‘4’ | ‘3’ | ‘2’ | ‘1’ |
其中d.a和d.b占用d低位一个字节(00110000),d.a : 10000, d.b : 001
d.a内存中二进制表示为10000,由于d.a为有符号的整型变量,输出时要对符号位进行扩展,所以结果为-16(二进制为11111111111111111111111111110000)
d.b内存中二进制表示为001,由于d.b为有符号的整型变量,输出时要对符号位进行扩展,所以结果为1(二进制为00000000000000000000000000000001)
《Soloe@csdn,转载请说明》
最后给出一个面试的案例:
struct mybitfields
{
unsigned short a : 4;
unsigned short b : 5;
unsigned short c : 7;
} test
void main(void)
{
int i;
test.a=2;
test.b=3;
test.c=0;
i=*((short *)&test);
printf("%d\n",i);
}
聪明的你,能直接在评论中给出答案吗?