预处理机制

news/2024/11/29 16:33:13/

跟着肯哥(不是我)学预处理机制

预处理类别

宏定义:#define

  • 将文本替换为表达式或语句

条件编译:#ifdef#ifndef#if#elif#endif

  • 根据标识符是否被定义选择编译代码

头文件包含:#include

  • 将其他文件(通常是头文件)包含到当前文件中,以便在当前文件中使用头文件中定义的内容

预处理流程

  1. 预处理指令识别
  2. 宏替换
  3. 条件编译
  4. 头文件包含
  5. 行连接处理
  6. 宏展开和条件编译的递归处理

预处理指令识别

扫描源代码并识别以#开头的预处理指令。

宏替换

预处理器根据宏定义将代码中的宏名称替换为指定的文本。
可以是常量替换,也可以是带参数的宏函数替换
预处理器会根据宏定义展开宏

条件编译

根据条件选择性地编译不同的代码块。
#ifdef#ifndef#if#elif#endif

头文件包含

通过#include指令,将其他文件(通常是头文件)包含到当前文件中,以便在当前文件中使用头文件中定义的内容

预处理的行连接处理

在C语言中,行连接处理是预处理阶段的一部分,用于将一行代码书写为多行,以保持代码可读性。
行连接操作通过反斜杠\字符实现。一行代码以反斜杠字符结尾时,该行代码将与下一行自动连接为一行。
image.png
换行之后的进位也会被当作空格输出出来。
行连接在预处理阶段,在编译阶段看到代码时,已经是连接在一起的一行。这种处理不会影响编译器的语义分析和中间代码。

宏展开和条件编译的递归处理

在进行宏展开和条件编译时,如果遇到新的预处理指令,预处理器会递归地处理这些指令。肯呢个会触发更多的宏展开和条件编译。

删除注释

预处理器将源代码中的注释删除,注释在预处理阶段无需保留,不会影响编译器的输出。

预编译的警告信息和错误信息

可以使用#error#warning预处理指令来生成编译错误和警告信息。这些指令在预处理时发出特定的错误或警告信息,让开发者知道代码中存在的问题或需要注意的地方
image.png
#error#warning指令生成的信息只会在预处理阶段发出,而不会影响到最终的目标代码,它们在编译阶段不会生成任何错误或警告信息。
image.png

查看预处理后的源文件

以肯哥用的GCC为例。
可以使用-E选项来查看预处理后的源文件。只进行预处理操作,不进行编译、汇编和链接。将预处理后的源文件输出到标准输出流,一般是控制台。
gcc -E example.c
编译器会将预处理后的内容输出到控制台。
如果你想将预处理后的源文件保存到一个文件中,可以使用重定向操作符>将输出重定向到一个文件中。
gcc -E example.c > preprocessed.c
上述命令会将预处理后的源文件保存到名为preprocessed.c的文件中。

重点强调

  • 宏定义的命名规范
  • 宏定义与函数调用的冲突
  • #include不单单是只能包含头文件:include的本质就是纯文本包含。
  • 善用条件编译:在庞大工程代码的配置裁剪工作中,绝大多数的技术手段就是利用条件编译,对不同的代码选用和删除,达到代码裁剪的效果。

http://www.ppmy.cn/news/1236785.html

相关文章

vue 获取元素的大小信息

在模板中为元素添加一个ref属性&#xff1a; <template> <div ref"myElement">Hello, World!</div> </template> 然后&#xff0c;在组件的setup函数中使用ref获取元素&#xff0c;并获取元素的信息&#xff1a; vue2获取方式&#xf…

『亚马逊云科技产品测评』活动征文|通过Lightsail搭建个人笔记

提示&#xff1a;授权声明&#xff1a;本篇文章授权活动官方亚马逊云科技文章转发、改写权&#xff0c;包括不限于在 Developer Centre, 知乎&#xff0c;自媒体平台&#xff0c;第三方开发者媒体等亚马逊云科技官方渠道 文章目录 前言实践知识储备Lightsail介绍Leanote介绍实践…

Qt实现自定义IP地址输入控件(百分百还原Windows 10网络地址输入框)

在开发网络相关的程序时,我们经常需要输入IP地址,例如源地址和目标地址。Qt提供了一些基础的控件,如QLineEdit,但是它们并不能满足我们对IP地址输入的要求,例如限制输入的格式、自动跳转到下一个输入框、处理回车和退格键等。因此,我们需要自己编写一个自定义的IP地址输入…

Docker可视化管理界面工具Portainer安装

Portainer是Docker容器管理界面工具&#xff0c;可以直观的管理Docker。 部署也很简单&#xff1a; 官方安装文档地址 1、创建数据卷 docker volume create portainer_data2、下载允许容器 docker run -d -p 8000:8000 -p 9443:9443 --name portainer --restartalways -v /v…

执行shell脚本提示syntax error: unexpected end of file

具体报错如下&#xff1a; ./test.sh: line 36: syntax error: unexpected end of file执行命令时需将test.sh替换为实际的脚本文件名称。 情形一&#xff1a; shell脚本在Windows下编写&#xff0c;上传到Linux上执行&#xff0c;由于 fileformat 类型不同&#xff0c;所以报…

数据提取PDF SDK的对比推荐

PDF 已迅速成为跨各种平台共享和分发文档的首选格式&#xff0c;它作为一种数据来源&#xff0c;常见于公司的各种报告和报表中。为了能更好地分析、处理这些数据信息&#xff0c;我们需要检测和提取 PDF 中的数据&#xff0c;并将其转换为可用且有意义的格式。而数据提取的 PD…

Redis报错:JedisConnectionException: Could not get a resource from the pool

1、问题描述&#xff1a; redis.clients.jedis.exceptions.JedisConnectionException: Could not get a resource from the pool 2、简要分析&#xff1a; redis.clients.util.Pool.getResource会从JedisPool实例池中返回一个可用的redis连接。分析源码可知JedisPool 继承了 r…

hadoop 常用端口号,常用配置文件都有哪些?hadoop3.x端口号 hadoop(十二)

1. hadoop3.x系列常用端口号&#xff1a; 类型desc端口hdfs NameNode内部通常端口号8020/9000/9820 hdfs NameNode 对用户的查询端口9870yarn查看历史任务运行情况8088历史服务器19888 2. hadoop 2.x系列常用端口号&#xff1a; 类型desc端口 hdfs NameNode 内部通常端口802…