一 方式1:采用offsetof宏
#include <stdio.h>
#include <stddef.h>
struct PP {
char a;
int b;
};
int main() {
struct PP pp;
printf("%zd\n", offsetof(struct PP, b)); // 输出4
return 0;
}
以上方法是调用系统宏offsetof,此宏是被定义在头文件stddef.h中,需要注意是编译器采用了内部填充机制,即上述代码在centos 7 64机器编译运行后,输出结果是4,char a后编译器填充了3个字节的数据(应该都是0)。此方法不能对位域取offset,即将上面代码int b换成int b:8,会编译出错。
二 方式2:自定义offsetof宏
#define OFFSETOF(type, f) ((size_t)((char *)&((type *)0)->f - (char *)(type *)0))
方法2假定地址0开始处有一个type类型结构体,由于没有对地址0做取值操作,因此不会发生内存访问错误,但此方法不能保证可移植性,也不能对位域取偏移量。