1.如果某个机器的整型值长度为4个字节,那么结构体的起始存储位置必须能被4整除。
2.编译器按照成员列表的顺序一个接一个地给每个成员分配内存。其中对于各个成员,编译器根据其类型分配赋予对其要求,比如char成员,按地址能被1整除对齐;short成员,按地址能被2整除对齐;int成员,按地址能被4整除对齐......
3.编译器在存储结构体成员时,为了满足各个成员的正确边界对齐要求,会在成员之间添加用于填充的额外内存空间。
4.举个例子:
- struct test {
- char a;
- int b;
- char c;
- }
内存布局如下:
有时,我们有充分的理由,决定不对结构体的成员进行重排以减少因对齐带来的空间损失。例如,我们可能想把相关的结构成员存储在一起,提高程序的可维护性和可读性。但是,如果不存在这样的理由,结构的成员应该根据他们的边界需要进行排列,减少因边界对齐而造成的内存损失。
特别的,在某些情况下,我们必须按照严格的边界对齐要求来定义结构体以获取正确的数据,比如:考虑解析BMP图片的代码例子。
RGB24(RGB888)生成BMP图片代码_denglin12315的博客-CSDN博客
关于header的定义1(包括3个部分):
- 1. 2字节的字符
- 2. BITMAPFILEHEADER部分
- typedef struct /**** BMP file header structure ****/
- {
- unsigned int bfSize; /* Size of file */
- unsigned short bfReserved1; /* Reserved */
- unsigned short bfReserved2; /* ... */
- unsigned int bfOffBits; /* Offset to bitmap data */
- } BITMAPFILEHEADER1;
-
- 3.BITMAPINFOHEADER部分
- typedef struct /**** BMP file info structure ****/
- {
- unsigned int biSize; /* Size of info header */
- int biWidth; /* Width of image */
- int biHeight; /* Height of image */
- unsigned short biPlanes; /* Number of color planes */
- unsigned short biBitCount; /* Number of bits per pixel */
- unsigned int biCompression; /* Type of compression to use */
- unsigned int biSizeImage; /* Size of image data */
- int biXPelsPerMeter; /* X pixels per meter */
- int biYPelsPerMeter; /* Y pixels per meter */
- unsigned int biClrUsed; /* Number of colors used */
- unsigned int biClrImportant; /* Number of important colors */
- } BITMAPINFOHEADER1;
关于header的定义2:
- typedef struct /**** BMP file info structure ****/
- {
- char simbol[2]
- unsigned int bfSize; /* Size of file */
- unsigned short bfReserved1; /* Reserved */
- unsigned short bfReserved2; /* ... */
- unsigned int bfOffBits; /* Offset to bitmap data */
- unsigned int biSize; /* Size of info header */
- int biWidth; /* Width of image */
- int biHeight; /* Height of image */
- unsigned short biPlanes; /* Number of color planes */
- unsigned short biBitCount; /* Number of bits per pixel */
- unsigned int biCompression; /* Type of compression to use */
- unsigned int biSizeImage; /* Size of image data */
- int biXPelsPerMeter; /* X pixels per meter */
- int biYPelsPerMeter; /* Y pixels per meter */
- unsigned int biClrUsed; /* Number of colors used */
- unsigned int biClrImportant; /* Number of important colors */
- } BITMAPINFOHEADER2;
这里直接说答案并提问: 为什么不能按照定义2的方式,而非要按照按照定义1的方式?定义2不是更简单直观吗?
答案提示:比较一下 2 + sizeof(BITMAPFILEHEADER1) + sizeof(BITMAPINFOHEADER1) 与
sizeof(BITMAPINFOHEADER2)的大小,标准bmp文件头的大小应该是和2 + sizeof(BITMAPFILEHEADER1) + sizeof(BITMAPINFOHEADER1)的值相等。出现以上差异的原因就是结构体对齐机制导致的。
1.sizeof()
2.offsetof(type, member) ——— 定义于stddef.h文件