【C语言深度解剖】预定义章节经典面试题讲解(offsetof宏模拟实现)【超详细的解释和注释】

那么这里博主先安利一下一些干货满满的专栏啦!

作者: #西城s
这是我的主页:#西城s
在食用这篇博客之前,博主在这里介绍一下其它高质量的编程学习栏目:
数据结构专栏:数据结构 这里包含了博主很多的数据结构学习上的总结,每一篇都是超级用心编写的,有兴趣的伙伴们都支持一下吧!
算法专栏:算法 这里可以说是博主的刷题历程,里面总结了一些经典的力扣上的题目,和算法实现的总结,对考试和竞赛都是很有帮助的!
力扣刷题专栏:Leetcode想要冲击ACM、蓝桥杯或者大学生程序设计竞赛的伙伴,这里面都是博主的刷题记录,希望对你们有帮助!
C的深度解剖专栏:C语言的深度解剖想要深度学习C语言里面所蕴含的各种智慧,各种功能的底层实现的初学者们,相信这个专栏对你们会有帮助的!

今天博主将带大家做一些预定义章节的面试题,带大家熟悉和深度掌握预定义章节

本篇位不收藏必后悔系列篇~

前言

关于预定义内容的两篇详细介绍,同样是干货满满的文章,不要错过噢~

【C语言深度解剖】一篇解决程序的环境【编译+链接详解】让面试官给我们竖起大拇指
【预定义】C语言预定义代码(宏、条件编译等)内容介绍【最全的保姆级别教程】

题目1

  • 设有以下宏定义:
    #define N 4
    #define Y(n) ((N+2)*n) (这种定义在编程规范中是严格禁止的)则执行语句:z = 2 * (N + Y(5 + 1)); 后,z的值为____

这题考察的其实是对宏在预处理阶段的替换方式的理解:宏在预处理阶段,是进行原封不动的替换的。
如果对这方面内容有疑问的伙伴们,可以通过博主的传送门食用上面两篇文章,这里面有非常非常详细的讲解:

所以这里宏的调用进行原封不动的替换后的结果为:
2*(4+((4+2)*5+1)

#define N 4
#define Y(n) ((N+2)*n)
int main() {
int z = 2 * (N + Y(5 + 1));
//2*(4+((4+2)*5+1)
//70
printf("%d\n", z);
return 0;
}

实现宏-交换一个数二进制位中奇数位和偶数位

思考:
我们要交换奇数位和偶数位,首先我们先要将某个数的奇数位和偶数位提取出来吧

  • 首先,我们发现,一个数字比如15:
    00000000000000000000000000001111如果按位与上一个01010101...0101这样一个数字,就可以将数字二进制中的奇数位提取出来。
  • 同理,我们发现,一个数字按位与上一个1010....1010这样一个数字之后,我们就可以将它的偶数位提取出来
  • 01010101...01这个数字表示成16进制就是0x55555555,同理,101010...1010这个数字表示成16进制就是0xaaaaaaaa
  • 当我们分别按位与完之后,奇数位向左移一位,偶数位向右移一位,再相加,我们就能得到我们的结果了。
//写一个宏,可以将一个整数的二进制位的奇数位和偶数位交换。
#if 1
#define __SWAP_BIT(num) num=((num&0x55555555)<<1)+((num&0xaaaaaaaa)>>1)
int main() {
int num = 10;
//00000000000000000000000000001111
//我们发现,我们只需要按位与一个01010101...01的数字,奇数位就留下了
//同样,如果将0101...01这个数字向左移动一位,就可以再按位与num就可以留下偶数位了
//01010101010101010101010101010101
//0x55555555
__SWAP_BIT(num);
printf("%d\n", num);
return 0;
}
#endif

offsetof宏的模拟实现

offsetof宏的使用

作用:计算结构体中某变量相对于首地址的偏移
所要包含的头文件:#include<stddef.h>

图片来自www.cplusplus.com

使用举例:
这里的输出结果涉及到结构体内存对齐方面的内容,伙伴们可以自行了解一下先,后面博主会专门出一期博客讲解这方面的内容。

#include<stddef.h>
struct S {
int a;
char c;
double d;
};
int main() {
printf("%d\n", offsetof(struct S, a));//0
printf("%d\n", offsetof(struct S, c));//4
printf("%d\n", offsetof(struct S, d));//8
return 0;
}

模拟实现:
实现:#define __OFFSETOF(st_type,mem_name) (size_t)&(((st_type*)0)->mem_name)

#include<stddef.h>
//写一个宏,计算结构体中某变量相对于首地址的偏移,并给出说明
//考察:offsetof宏的实现
struct S {
int a;
char c;
double d;
};
#define __OFFSETOF(st_type,mem_name) (size_t)&(((st_type*)0)->mem_name)
int main() {
printf("%d\n", __OFFSETOF(struct S, a));
printf("%d\n", __OFFSETOF(struct S, c));
printf("%d\n", __OFFSETOF(struct S, d));
return 0;
}

尾声

到这里就是本期博客的全部内容了,当然,关于这方面的具体内容知识点,可以通过博主通过的传送门进行详细了解噢~
【C语言深度解剖】一篇解决程序的环境【编译+链接详解】让面试官给我们竖起大拇指
【预定义】C语言预定义代码(宏、条件编译等)内容介绍【最全的保姆级别教程】
如果你感觉这篇博客对你有帮助的话,不要忘了一键三连:点赞收藏关注噢~

【C语言深度解剖】预定义章节经典面试题讲解(offsetof宏模拟实现)【超详细的解释和注释】的更多相关文章

  1. C语言深度解剖读书笔记(6.函数的核心)

    对于本节的函数内容其实就没什么难点了,但是对于函数这节又涉及到了顺序点的问题,我觉得可以还是忽略吧. 本节知识点: 1.函数中的顺序点:f(k,k++);  这样的问题大多跟编译器有关,不要去刻意追求 ...

  2. C语言深度解剖读书笔记

    开始本节学习笔记之前,先说几句题外话.其实对于C语言深度解剖这本书来说,看完了有一段时间了,一直没有时间来写这篇博客.正巧还刚刚看完了国嵌唐老师的C语言视频,觉得两者是异曲同工,所以就把两者一起记录下 ...

  3. 【转】 C语言深度解剖读书笔记(1.关键字的秘密)

    本文出处:http://blog.csdn.net/mbh_1991/article/details/10149805 开始本节学习笔记之前,先说几句题外话.其实对于C语言深度解剖这本书来说,看完了有 ...

  4. 《C语言深度解剖》学习笔记之关键字

    第一章 关键字 C语言共有32个关键字. 关键字   auto 声明自动变量 int 声明整型变量 long 声明长整型变量 char 声明字符型变量 float 声明浮点型变量 short 声明短整 ...

  5. 《C语言深度解剖》面试题整理

    请在40分钟内完成以下20道C语言基础题.在没有任何提示的情况下,如果能得满分,那么你可以扔掉本书了,你的水平已经大大超过了作者:如果能的80分以上,说明你的C语言基础还不错,学习本书可能会比较轻松: ...

  6. c语言深度解剖(笔记)

    1.1最宽恒大量的关键字----auto 函数内部变量,限制作用域为这个 1.2.1最快的关键字---- register函数. 关键字请求编译器尽可能的将变量存在 CPU 内部寄存器中 1.2.2使 ...

  7. 《C语言深度解剖》学习笔记之函数

    第6章 函数 1.编码风格 [规则6-1]每一个函数都必须有注释 [规则6-2]每个函数定义之后以及每个文件结束之后都要加若干个空行 [规则6-3]在一个函数体内,变量定义与函数语句之间要加空行 [规 ...

  8. 《C语言深度解剖》学习笔记之内存管理

    第5章 内存管理 1.野指针 定义指针变量的同时最好初始化为NULL,用完指针后也将变量的值设置为NULL.也就是说除了使用时,别的时间都把它设置为NULL 2.堆,栈和静态区 堆:由malloc系列 ...

  9. 《C语言深度解剖》学习笔记之指针和数组

    第4章 指针和数组 1. int *p=NULL 和 *p=NULL 有什么区别 int *p = NULL; 第一句代码的意思是:定义一个指针变量p,其指向的内存里面保存的是 int类型的数据:在定 ...

  10. 《C语言深度解剖》学习笔记之预处理

    第3章 预处理 1.下面两行代码都是错的.因为注释先于预处理指令被处理,当这两行被展开成“//……”和“/*……*/”时,注释已处理完毕,所以出现错误 #define BSC // #define B ...

随机推荐

  1. The 18th Zhejiang Provincial Collegiate Programming Contest 补题记录(ACFGJLM)

    补题链接:Here A. League of Legends 签到题,求和判断即可 ll suma, sumb; void solve() { ll x; for (int i = 1; i < ...

  2. 【收藏】Stable Diffusion 制作光影文字效果

    大家对于最近 Stable Diffusion 不断出新的视觉"整活"印象都很深刻,很多人对最近比较流行的制作光影文字很感兴趣,制作光影文字可以作为进阶 Stable Diffus ...

  3. 如何通过canvas实现电子签名

    想要实现一个电子签名,可以支持鼠标签名,还能类似书法效果线条有粗有细,同时可以导出成图片. 一.实现连贯的划线 1)首先需要注册鼠标下压.鼠标放开.鼠标移出和鼠标移动事件,通过鼠标下压赋值downFl ...

  4. Visual Studio2019 使用WCF服务

    什么是WCF Windows Communication Foundation (WCF) 是一个框架,用于生成面向服务的应用程序.它取代了较旧的进程间通信技术,例如 ASMX Web 服务..NET ...

  5. ASIC 功能验证VTB

    目标 设计流程 验证设计文档和RTL code之间的关系 RTL code(DUT) - 可以当作是一个黑盒,DUT内部是完全不可见的 白盒验证 - DUT内部RTL完全可见 灰盒验证 - DUT内部 ...

  6. Chrome/Edge 设置黑色主题

    Chrome chrome://flags/#enable-force-dark Edge edge://flags/#enable-force-dark

  7. [转帖]prometheus的TCP alloc取值

    prometheus的TCP alloc取值 sockets: used:已使用的所有协议套接字总量 TCP: orphan:无主(不属于任何进程)的TCP连接数(无用.待销毁的TCP socket数 ...

  8. [转帖]总结:Springboot监控Actuator相关

    一.介绍 由于项目中使用的仍然是比较老旧的1.5.6版本,所以本文是基于此版本进行描述. 二.Actuator使用 ActuatorActuator是Spring Boot提供的对应用系统的监控和管理 ...

  9. 银河麒麟(Ubuntu)无法上网问题的解决方法

    最近部门借了几台银河麒麟的服务器. 因为有特殊用途, 不允许连接互联网,所以没办法只能搭建一个小的局域网进行处理. 但是发现在搭建过程中遇到了一些坑, 之前协助同事解决odoo问题时也遇到过, 当时本 ...

  10. 没有虚拟DOM版本的vue(Vue Vapor)

    前言 随着Svelte和SolidJS的流行,无虚拟DOM模式逐渐开始火了起来.vue也推出了无虚拟DOM模式的版本,就是我们今天要讲的Vue Vapor. 什么是Vue Vapor Vue Vapo ...