我写了这个程序:
#include <stdlib.h>
#include <stdio.h>
#include <stdbool.h>
struct A {
bool a;
bool b;
bool c;
bool d;
};
struct B {
int a;
};
int main() {
struct A* pa = malloc( sizeof(struct A) );
struct B* pb = (struct B*) pa;
pa->a = 0;
pa->b = 1;
pa->c = 0;
pa->d = 0;
printf("value of pint is %i\n", pb->a);
return 0;
}
我希望它打印2(0010)但是输出是256.任何一个云都有助于解释这段代码有什么问题?
答案 0 :(得分:3)
我希望它打印2(0010)但是输出是256.任何一个云都有助于解释这段代码有什么问题?
bool
占用至少一个字节。在你的情况下,显然只有一个字节,你的平台是little-endian(8位char
)。因此,第二个(最低有效)字节为1,所有其他字节为0,使1*256
。
请注意,pa
和pb
的类型惩罚违反了严格的别名。
使用union
便携式输入双关语。
答案 1 :(得分:2)
初始化pa
后,您有
*pa = { 0x00, 0x01, 0x00, 0x00 }
因为每个bool是一个字节。当你将它转换为int值时,你得到(在小端机器中)*pb
为
*pb = 0x00000100
显然是256
。知道了吗?
如果需要,您可以将struct A
定义为:
struct A {
bool a:1;
bool b:1;
bool c:1;
bool d:1;
};
但是不要将struct A
的指针强加到struct B
的指针,因为两个结构的大小都是不同的。
这可能对您将来有所帮助:
union A {
struct {
bool bit0:1;
bool bit1:1;
bool bit2:1;
bool bit3:1;
bool bit4:1;
bool bit5:1;
bool bit6:1;
bool bit7:1;
};
unsigned char cByte;
};
通过定义,您可以按位或按字节访问它。
答案 2 :(得分:1)
%i
打印一个整数。
bool是一个无符号整数类型,足以存储值0和1.
你可以这样打印bool:
printf("%d\n", b);
答案 3 :(得分:1)
您正在以小Endian表示法打印该数字。实际上,你打印的是:
0 * 256^0 + 1 * 256^1 + 0 * 256^2 + 0 * 256^3
如果您决定使用位域(如其他人所建议的那样),则应使用%x
以十六进制打印。如果您严格要以二进制打印,则必须使用循环遍历各个位。
答案 4 :(得分:0)
尝试
struct A {
bool a:1;
bool b:1;
bool c:1;
bool d:1;
};
:1
部分强制编译器为每个成员变量分配1位而不是1字节,因此struct A的内存布局看起来像这样(假设小端):
|-byte 1-|-byte 2-|-byte 3-|-byte 3-|
uuuudcba uuuuuuuu uuuuuuuu uuuuuuuu
其中u
捐赠未使用的。当将它转换为整数时,您将得到一个整数视图:
uuuuuuuu uuuuuuuu uuuuuuuu uuuudcba
由于不同编译器实现的位顺序不同,您也可能得到反转结果4(0100)而不是2(0010)