为什么一个字符只有 1 个填充字节(在 32 位机器上)?
Why is there only 1 padding byte for a char (on a 32-bit machine)?
A tutorial on data padding 表示下面 C 结构中 int i
后面的 char c
需要 1 个填充字节。
struct test2
{
int i;
// 4 bytes
char c;
// 1 byte
// 1 padding byte. <-- question here
short s;
// 2 bytes
};
考虑到在这种情况下内存访问是 32 位的,我想了解为什么不是 3 字节填充?
每个成员的对齐方式才是最重要的。考虑每种类型的对齐要求。对于 int
,在您的情况下,它是 4
字节。一个char
,自然是1
。 short
怎么样?那么在您的体系结构上,它似乎是 2
字节。我们希望每个成员都根据自己的对齐要求对齐。
因为 int
是第一个成员,我们不需要任何填充(但这确实会影响 struct
的整体大小)。然后,我们有一个char
,它的要求最宽松,所以我们不需要为它填充。然后是short
。它需要对齐到 2 个字节。我们目前处于 5 个字节的偏移量,因此我们需要一个填充字节来使 short
正确对齐。总而言之,这给了我们 8 个字节,并且也符合整个结构的对齐方式,所以最后不需要额外的填充。
一般来说,结构的最小尺寸将通过从最强对齐要求到最弱排列成员来实现。这不一定是获得最小尺寸的唯一顺序,但可以保证没有其他顺序会更小。
Unaligned memory accesses occur when you try to read N bytes of data
starting from an address that is not evenly divisible by N (i.e. addr
% N != 0). For example, reading 4 bytes of data from address 0x10004
is fine, but reading 4 bytes of data from address 0x10005 would be an
unaligned memory access.
int
大小为4字节,short
大小为2字节,char
大小为1字节(64位系统)。
假设起始地址为 0x0000。
所以,int i
占用0x0000到0x0003。
char c
存储在 0x0004(因为地址可以被 1 整除)。
假设char c
后没有1字节填充,那么short s
会被存放在0x0005处,不能被2整除,这会导致内存访问不对齐
为了防止这种情况,我们在 char c
之后添加了 1 个字节的填充。填充1个字节后,short s
将被存储为0x0006,被2整除。
A tutorial on data padding 表示下面 C 结构中 int i
后面的 char c
需要 1 个填充字节。
struct test2
{
int i;
// 4 bytes
char c;
// 1 byte
// 1 padding byte. <-- question here
short s;
// 2 bytes
};
考虑到在这种情况下内存访问是 32 位的,我想了解为什么不是 3 字节填充?
每个成员的对齐方式才是最重要的。考虑每种类型的对齐要求。对于 int
,在您的情况下,它是 4
字节。一个char
,自然是1
。 short
怎么样?那么在您的体系结构上,它似乎是 2
字节。我们希望每个成员都根据自己的对齐要求对齐。
因为 int
是第一个成员,我们不需要任何填充(但这确实会影响 struct
的整体大小)。然后,我们有一个char
,它的要求最宽松,所以我们不需要为它填充。然后是short
。它需要对齐到 2 个字节。我们目前处于 5 个字节的偏移量,因此我们需要一个填充字节来使 short
正确对齐。总而言之,这给了我们 8 个字节,并且也符合整个结构的对齐方式,所以最后不需要额外的填充。
一般来说,结构的最小尺寸将通过从最强对齐要求到最弱排列成员来实现。这不一定是获得最小尺寸的唯一顺序,但可以保证没有其他顺序会更小。
Unaligned memory accesses occur when you try to read N bytes of data starting from an address that is not evenly divisible by N (i.e. addr % N != 0). For example, reading 4 bytes of data from address 0x10004 is fine, but reading 4 bytes of data from address 0x10005 would be an unaligned memory access.
int
大小为4字节,short
大小为2字节,char
大小为1字节(64位系统)。
假设起始地址为 0x0000。
所以,int i
占用0x0000到0x0003。
char c
存储在 0x0004(因为地址可以被 1 整除)。
假设char c
后没有1字节填充,那么short s
会被存放在0x0005处,不能被2整除,这会导致内存访问不对齐
为了防止这种情况,我们在 char c
之后添加了 1 个字节的填充。填充1个字节后,short s
将被存储为0x0006,被2整除。