我对C中结构的行为有疑问。
以给定的结构为例:
typedef struct {
char num1;
char num2;
} structa;
typedef struct {
structa innerstruct;
char num3;
char num4;
} structb;
我假设,因为structb包含一个structa字段,而不是指向一个字段的指针,所以structb将在内存中布局:
struct {
char num1; //innerstruct num1
char num2; //innerstruct num2
char num3; //num3
char num4; //num4
};
如果是这样,你可以像这样访问每个字段吗?
*(((char *)&structbvar) + 0) = 1; //innerstruct num1
*(((char *)&structbvar) + 1) = 2; //innerstruct num2
*(((char *)&structbvar) + 2) = 3; //num3
*(((char *)&structbvar) + 3) = 4; //num4
或像这样访问它们?
((structa)structbvar).num1 = 1; //innerstruct num1
((structa)structbvar).num2 = 2; //innerstruct num2
无论这是不好的做法。
它还可靠/便携吗?
编辑,正如Matt McNabb指出的那样,你不能直接施放结构,所以它应该是:
((structa *)&structbvar)->num1 = 1; //innerstruct num1
((structa *)&structbvar)->num2 = 2; //innerstruct num2
答案 0 :(得分:2)
*(char *)
版本定义明确,但您需要在innerstruct
结束后num3
之前检查填充。
(structa)structbvar
格式不正确。我认为*(structa *)&structbvar
会好的,因为关于具有共同初始序列的结构的规则(尽管我会仔细检查并更新我的答案)。然而,这有点无意义,因为你可以写structbvar.innerstruct
。
答案 1 :(得分:2)
如果使用指针强制访问struct字段,代码的可靠性取决于内存的对齐方式。所以不建议这样做,除非你强迫内存按预期对齐。
在不调用嵌套结构名称的情况下访问字段的另一种方法是使用带有union的Anonymous Struct。它是C99标准版,当然也是便携和可靠的,除了你的编译器不支持C99。
您可以使用Anonymous Strct定义一个联合:
typedef union {
uint32_t wWord;
struct {
uint16_t hwLow;
uint16_t hwHigh;
};
} test_t;
然后像这样访问每个字段:
test_t tTest;
tTest.wWord = 0x00FF0000;
此外:
tTest.hwHigh = 0x00FF;