__builtin_offsetof()[通俗易懂]

__builtin_offsetof()[通俗易懂]————-linuxcompiler-gcc4.h————–#define__compiler_offsetof(a,b)__builtin_offsetof(a,b)分析准备:__compiler_offsetof(),为gcc编译器中的编译方面的参数,查阅gcc方面的文档:—>gcc.pdf.Downloadfromwww.gn

大家好,又见面了,我是你们的朋友全栈君。如果您正在找激活码,请点击查看最新教程,关注关注公众号 “全栈程序员社区” 获取激活教程,可能之前旧版本教程已经失效.最新Idea2022.1教程亲测有效,一键激活。

Jetbrains全系列IDE使用 1年只要46元 售后保障 童叟无欺

本文转载自  :  https://blog.csdn.net/rockhui/article/details/6304705 

————-linuxcompiler-gcc4.h————–
#define __compiler_offsetof(a,b) __builtin_offsetof(a,b)
分析准备:__compiler_offsetof(),为gcc编译器中的编译方面的参数,查阅gcc方面的文档:
—>gcc.pdf.Download from www.gnu.org 。其中解释如下:
#define offsetof(type, member) __builtin_offsetof (type, member)

自己分析:即:__builtin_offsetof(a,b)就是#define offsetof(TYPE, MEMBER) ((size_t) &((TYPE *)0)->MEMBER)。__builtin_offsetof(a,b)和offsetof(TYPE,MEMBER)本质一样的,只是 offsetof()宏是由程序员自己来设计(详见后面讲解)。而__builtin_offsetof()宏就是在编译器中已经设计好了的函数,直接调用即可。明白了这个区别后,下面的代码很好理解。

——-linuxstddef.h—–offsetof()———–
#define __compiler_offsetof(a,b) __builtin_offsetof(a,b)
——————————-
#undef offsetof
#ifdef __compiler_offsetof
#define offsetof(TYPE,MEMBER) __compiler_offsetof(TYPE,MEMBER)
#else
#define offsetof(TYPE, MEMBER) ((size_t) &((TYPE *)0)->MEMBER)
#endif
1.对__compiler_offsetof()宏的分析:
__compiler_offsetof来确认编译器中是否内建了功能同offsetof()宏一样的宏。若已经内建了这样的宏,则 offsetof()就是使用这个内建宏__compiler_offsetof()即:__builtin_offsetof()宏。如果没有定义 __compiler_offsetof()宏,则offsetof()宏就由程序员来设计之。

2.对offsetof()宏的分析:(以下引用论坛)—曾经的腾讯QQ的笔试题。
宿舍舍友参加qq笔试,回来讨论一道选择题,求结构中成员偏移。
想起Linux内核链表,数据节点携带链表节点,通过链表访问数据的方法,用到offsetof宏,今天把它翻了出来:
#define offsetof(TYPE, MEMBER) ((size_t) & ((TYPE *)0)->MEMBER )

一共4步
1. ( (TYPE *)0 ) 将零转型为TYPE类型指针;
2. ((TYPE *)0)->MEMBER 访问结构中的数据成员;
3. &( ( (TYPE *)0 )->MEMBER )取出数据成员的地址;
4.(size_t)(&(((TYPE*)0)->MEMBER))结果转换类型.巧妙之处在于将0转换成(TYPE*),结构以内存空间首地址0作为起始地址,则成员地址自然为偏移地址;
举例说明:
#include<stdio.h>
typedef struct _test
{

char i;
int j;
char k;
}Test;
int main()
{

Test *p = 0;
printf(“%p “, &(p->k));
}
自己分析:这里使用的是一个利用编译器技术的小技巧,即先求得结构成员变量在结构体中的相对于结构体的首地址的偏移地址,然后根据结构体的首地址为0,从而得出该偏移地址就是该结构体变量在该结构体中的偏移,即:该结构体成员变量距离结构体首的距离。在offsetof()中,这个member成员的地址实际上就是type数据结构中member成员相对于结构变量的偏移量。对于给定一个结构,offsetof(type,member)是一个常量,list_entry()正是利用这个不变的偏移量来求得链表数据项的变量地址。

敬请高手指正。

版权声明:本文内容由互联网用户自发贡献,该文观点仅代表作者本人。本站仅提供信息存储空间服务,不拥有所有权,不承担相关法律责任。如发现本站有涉嫌侵权/违法违规的内容, 请联系我们举报,一经查实,本站将立刻删除。

发布者:全栈程序员-站长,转载请注明出处:https://javaforall.net/172103.html原文链接:https://javaforall.net

(0)
上一篇 2022年8月22日 上午9:46
下一篇 2022年8月22日 上午10:00


相关推荐

  • 数论概论读书笔记 23.二次互反律的证明

    数论概论读书笔记 23.二次互反律的证明二次互反律的证明二次互反定律有三部分 第一部分告诉我们 1 1 1 何时是二次剩余 第二部分告诉我们 222 何时是二次剩余 第三部分告诉我们 精简一下 pq qp 1 p 12 q 12 pq qp 1 p 12 q 12 left frac p q right left frac q p right 1 frac p 1 2 cdo

    2026年3月20日
    4
  • php将字符串进行ASCII升序排列[通俗易懂]

    php将字符串进行ASCII升序排列[通俗易懂]php将字符串进行ASCII升序排列

    2022年4月24日
    41
  • 腾讯云免费ssl_腾讯云ssl证书申请

    腾讯云免费ssl_腾讯云ssl证书申请1.点此进入SSL证书产品页面2.点击立即选购,进入产品配置界面。3.选择自定义配置–>国际标准–>域名型免费版,点击免费快速申请。4.进入登录界面,用微信扫二维码。5.填写域名相关信息,点击下一步6.选择域名的验证方式,推荐DNS验证,点击下一步。7.打开域名管理后台,根据上一步获得的域名解析信息,增加一条TXT类型的解析记录。8.回到腾讯云SSL证书申请界面,查看域名验证结果,验证成功会收到一条短信,反之会有提示错误。9.申

    2025年10月17日
    4
  • matlab三维图怎么改变颜色_matlab画复杂函数图像

    matlab三维图怎么改变颜色_matlab画复杂函数图像当我们学习surface命令时,已经看到了三维作图的一些端倪。在matlab中我么可以调用mesh(x,y,z)函数来产生三维图像。首先,我们用z=cos(x)sin(y)在-2pi≤x,y≤2pi内的图像来看看:[x,y]=meshgrid(-2*pi:0.1:2*pi);z=cos(x).*sin(y);mesh(x,y,z),xlabel(‘x’),ylabel(‘y’),zla…

    2022年8月31日
    8
  • 利用JDK发布webService实例「建议收藏」

    利用JDK发布webService实例「建议收藏」一、webService的发布1、新建一个webProject2、修改jdk为1.6及以上—-3、编写方法—- packagecom.test.webService;importjavax.jws.WebService;importjavax.xml.ws.Endpoint;@WebServicepublicclass

    2022年7月21日
    20
  • 推荐7个冷门手机APP,每一个都让我相见恨晚

    推荐7个冷门手机APP,每一个都让我相见恨晚推荐 7 个让我相见恨晚的手机 APP1 SmartKit360S 是一个全能的工具箱软件 只有 10M 的大小 却提供了 40 多个实用工具 有了它 就不需要下载这么多软件了 SmartKit360 的工具类别非常丰富 比如常用工具 新闻 社交 购物等等 它相比一个木函更加接地气一点 两者搭配起来使用更爽 并且支持在桌面上创建并添加快捷方式 让你手机秒变生产力工具百宝箱 2 智办事智办事是一款以目标为导向 以人为中心 以成果为标准的目标管理软件 将世界 500 强的工

    2025年9月29日
    4

发表回复

您的邮箱地址不会被公开。 必填项已用 * 标注

关注全栈程序员社区公众号