A_U*_*ser 15 c c++ unions c++11 c11
我在C中有一个这样的联盟:
union AUnion {
struct CharBuf {
char *buf;
size_t len;
} charbuf;
uint8_t num;
double fp_num;
};
Run Code Online (Sandbox Code Playgroud)
我的问题是,如果给出以下内容,我可以保证:
union AUnion u;
Run Code Online (Sandbox Code Playgroud)
那么以下是真的:
&u == &u.num
&u == &u.fp_num
&u == &u.charbuf
Run Code Online (Sandbox Code Playgroud)
即它们都从u存储的内存段的开头开始.
在编译这个C程序的情况下,gcc version 5.3.0与-std=c11上述是真实的:
#include <stdio.h>
#include <stdint.h>
#include <stdlib.h>
union AUnion {
struct CharBuf {
char *buf;
size_t len;
} charbuf;
uint8_t num;
double fp_num;
};
int main(void)
{
union AUnion u;
printf("%d\n", ((void*)&u) == ((void*)&u.charbuf));
printf("%d\n", ((void*)&u.charbuf) == ((void*)&u.num));
printf("%d\n", ((void*)&u.num) == ((void*)&u.fp_num));
}
Run Code Online (Sandbox Code Playgroud)
打印时:
1
1
1
Run Code Online (Sandbox Code Playgroud)
使用相同的编译器将上面的代码编译为C++ 11会产生与将其编译为C11相同的输出.
但这是标准化的行为吗?这是不确定的?我可以依赖大多数C编译器的这种行为吗?我可以期待C++编译器的这种行为吗?
too*_*ite 13
在6.7.2.1p16中,C标准保证:
联合的大小足以包含其最大的成员.最多一个成员的值可以随时存储在union对象中.指向适当转换的联合对象的指针指向其每个成员(或者如果成员是位字段,则指向它所在的单元),反之亦然.
所以,是的,你可以依赖从unions地址开始的所有成员(注意这对于a的第一个成员是相同的struct).
C++标准包含一个关于C风格(即只有C风格的成员)unions/structs 的类似句子,因为C++允许将unions 传递给需要这种布局的C函数.C++标准中的相关部分是9.5.
但是,请注意标准简单类型(整数,浮点数)中可能存在填充位.他们的内部可能会有所不同(结束).您还可能违反严格的别名规则(C:有效类型).
| 归档时间: |
|
| 查看次数: |
1380 次 |
| 最近记录: |