结构体和int等类型一样,都是数据类型。其他类型怎么转换,结构体就怎么转换,没有什么特殊的地方。
楼主可能想知道的不是结构体怎样强制转换这个问题吧,猜测,楼主想知道如下几个问题:
如果将一个结构体强制类型转换为另一个结构体(或者类型),那这个结构体的成员会怎样了?
如果将一个结构体强制类型转换为另一个结构体(或者类型),那么这个结构体成员的数值又会是什么了?
解答:
1、结构体的本质是:我们和C语言约定了一段内存空间的长短,及其内容的安排。假设下面两个结构体:
struct A1
{
int a;
char b;
};
struct A2
{
char a;
int b;
};
接着,用struct A1和struct A2定义变量,并赋初值:
struct A1 x = {10, 'A'};
struct A2 y = {'A', 10};
现在最重要的是,要知道x和y的内存情况:
x的内存安排是:前4B,后1B;
y的内存安排是:前1B,后4B。
如果有struct A2 z;
z.a = ((struct A2)x).a;
那么,C语言会对x的空间,按照struct A2的格局进行解释:
也就是说,将x的第一个字节看成第一个成员,且按ASCII码处理数据,而将后面的4B看成第二个成员,并按补码格式解释数据。
这涉及到内存布局,直接强转是不安全的.
1楼正解。但1楼给的例子有点问题,一般情况下编译器都会对结构体进行对齐,故两种结构体默认都是8字节大小。
简单的说,至于结构体对其之类的东西不做考虑,这部分内容可以看我的一片博文:
[c&cpp][memory] 内存对齐分配策略(含位域模式)
struct SC c1[]={{3},{4},{5},{6}};
struct SD *c2=(struct SD *)c1+1;
上面两句之后,C1占据48字节存储,在栈上,按照栈生长空间,存储内容可以看做:
3,0,0,4,0,0,5,0,0,6,0,0
(struct SD *)c1+1;首先将C1强制类型转换为SD指针,在+1的时候做指针偏移,是按照c1指向的数据类型的大小偏移的,也就是偏移4个字节,c1指向紧跟4之后的0。
struct SD *c2=(struct SD *)c1+1;操作使得c2指向c1的位置,也就是紧跟4的0,对于指针来说,他不关心自己指向的是什么,它会按照自己指向的类型信息来解释其指向的内存区域。所以说出的内容是0050。
这种强制类型转换是非常错误的,这里你的代码可以运行通过,是因为你的c1数组申请的足够大,在栈上申请了足够的空间供c2使用,否则,出错时必然的。
每个c1占3个int,c1指向的地址是 3,0,0,4,0,0,5,0,0,6,0,0
struct SC c1[]={{3},{4},{5},{6}};
struct SD *c2=(struct SD *)c1+1;
c1 + 1 相当于跨越了4个int(因为c1被转成SD的指针,1个SD是4个int),所以c2指向的数据是:
0,0,5,0,0,6,0,0
所以打印出来应该是0,0,5,0.