C语言---宏

news2025/1/12 0:52:18

专栏:C语言
个人主页:HaiFan.
专栏简介:本专栏主要更新一些C语言的基础知识,也会实现一些小游戏和通讯录,学时管理系统之类的,有兴趣的朋友可以关注一下。

#define

  • 预处理
    • 预定义符号
  • define
    • #define定义标识符
    • #define定义宏
    • #define替换规则
    • 带副作用的宏参数
    • 宏的缺点
    • 命名约定

预处理

预定义符号

__FILE__ //进行编译的源文件
__LINE__ //文件当前的行号
__DATE__ //文件被编译的日期
__TIME__ //文件被编译的时间
__STDC__ //如果编译器遵循ANSI C,其值为1,否则未定义

define

#define定义标识符

语法:
	#define name stuff

举个例子

#include <stdio.h>
#define MAX 1000
int main()
{
	printf("%d",MAX);
	return 0;
}

在这里插入图片描述

注:在define定义标识符的时候,不要在最后加上 ;
比如:#define MAX 1000;

这样容易导致一些问题。

#define定义宏

#define机制包括了一个规定,允许把参数替换到文本中,这种实现通常称为宏(macro)或定义宏(define macro)。

下面是宏的声明方式

#define name( parament-list ) stuff
//其中的 parament-list 是一个由逗号隔开的符号表,它们可能出现在stuff中

注意:
参数列表的左括号必须与name紧邻。
如果两者之间有任何空白存在,参数列表就会被解释为stuff的一部分。
比如:#define MUL(x) x*x

这个宏接收一个参数x,然后进行x*x的运算。
宏也有值得注意的地方。

#include <stdio.h>

#define MUL(x)  x*x*x

int main()
{
	printf("%d", MUL(5 + 1));
	return 0;
}

这个代码的结果是216吗?
在这里插入图片描述
为什么会是16??
因为宏是替换。它只是把x替换成了(5+1),但是在替换的时候并没有对(5+1)进行计算。实际上算的是:printf("%d", 5+1*5+1*5+1);,那么如何解决这个问题呢?只需要在宏定义上加上括号即可。

#include <stdio.h>

#define MUL(x)  (x)*(x)*(x)

int main()
{
	printf("%d", MUL(5 + 1));
	return 0;
}

这样,就能达到预期的效果了。

#define替换规则

在程序中扩展#define定义符号和宏时,需要涉及几个步骤。

  1. 在调用宏时,首先对参数进行检查,看看是否包含任何由#define定义的符号。如果是,它们首先
    被替换。
  2. 替换文本随后被插入到程序中原来文本的位置。对于宏,参数名被他们的值所替换。
  3. 最后,再次对结果文件进行扫描,看看它是否包含任何由#define定义的符号。如果是,就重复上
    述处理过程。

注意:

  1. 宏参数和#define 定义中可以出现其他#define定义的符号。但是对于宏,不能出现递归。
  2. 当预处理器搜索#define定义的符号的时候,字符串常量的内容并不被搜索。

带副作用的宏参数

当宏参数在宏的定义中出现超过一次的时候,如果参数带有副作用,那么你在使用这个宏的时候就可能出现危险,导致不可预测的后果。副作用就是表达式求值的时候出现的永久性效果。

x+1无副作用
x++有副作用
#include <stdio.h>
#define MAX(x, y) (x) > (y)? (x) : (y) 

int main()
{
	int a = 1;
	int b = 2;
	int ret = MAX(a++, b++);
	printf("a=%d,b=%d,ret=%d", a, b, ret);
	return 0;
}

这个代码的结果会是什么呢?
在这里插入图片描述
这里我们得知道预处理器处理之后的结果是什么:

ret = ( (x++) > (y++) ? (x++) : (y++));

宏是替换,直接把x和y替换成了a++和b++,所以会造成上面的问题。

宏的缺点

  1. 每次使用宏的时候,一份宏定义的代码将插入到程序中。除非宏比较短,否则可能大幅度增加程序
    的长度。
  2. 宏是没法调试的。
  3. 宏由于类型无关,也就不够严谨。
  4. 宏可能会带来运算符优先级的问题,导致程容易出现错。

命名约定

宏在命名的时候,要把宏名全大写
函数在命名的时候遵循驼峰原则

本文来自互联网用户投稿,该文观点仅代表作者本人,不代表本站立场。本站仅提供信息存储空间服务,不拥有所有权,不承担相关法律责任。如若转载,请注明出处:http://www.coloradmin.cn/o/331834.html

如若内容造成侵权/违法违规/事实不符,请联系多彩编程网进行投诉反馈,一经查实,立即删除!

相关文章

云片验证码分析思路

本文仅供学习参考&#xff0c;又不懂的可以联系博主 目标链接: aHR0cHM6Ly93d3cueXVucGlhbi5jb20vcHJvZHVjdC9jYXB0Y2hh接口分析 captcha/get 验证码图片获取接口&#xff0c;GET请求&#xff0c;包含四个参数cb、i、k、captchaId 接口返回&#xff0c;如果是滑动验证码&…

「敏捷建模」敏捷设计理念的纪律

本文概述了敏捷软件开发团队的设计策略。这些策略对于扩展敏捷软件开发以满足现代IT组织的实际需求至关重要。敏捷的设计方法与传统方法截然不同&#xff0c;显然也更有效。重要的是要了解&#xff1a; 敏捷设计实践 敏捷设计理念 整个敏捷生命周期的设计 1.敏捷设计实践 从高…

大数据概述

一、大数据时代 大数据时代 三次信息化浪潮&#xff1a;个人计算机80年-互联网95年-物联网、云计算和大数据(2010年) 发展时间较短&#xff0c;大数据人才缺失大数据人才 培训出来的&#xff1a;Java-》大数据 优点&#xff1a;对于大数据技术的细节会比较清楚 缺点&#xff1…

为什么Redis集群的最大槽数是16384个?

对于客户端请求的key&#xff0c;根据公式HASH_SLOTCRC16(key) mod 16384&#xff0c;计算出映射到哪个分片上&#xff0c;然后Redis会去相应的节点进行操作&#xff01; 为什么有16384个槽&#xff1f; Redis集群并没有使用一致性hash而是引入了哈希槽的概念。Redis 集群有16…

金仓数据库事务日志与检查点

事务日志与检查点 WAL文件&#xff0c;在金仓数据库中&#xff0c;事务日志文件称为Write Ahead Log&#xff08;预写式日志&#xff0c;简称WAL&#xff09;。 WAL存储了数据库系统中所有更改和操作的历史&#xff0c;相当于Oracle的REDO。 WAL机制是在这个写数据的过程中加…

[Android开发基础4] 意图与意图过滤器

文章目录 意图&#xff08;Intent&#xff09; 简介 显式意图 隐式意图 意图过滤器&#xff08;IntentFiler&#xff09; action data category 意图&#xff08;Intent&#xff09; 简介 Intent被称为意图&#xff0c;是程序中各组件进行交互的一种重要方式&#xff0c…

第四章.误差反向传播法—简单层的实现(加法层(AddLayer)+乘法层(MulLayer))

第四章.误差反向传播法 4.1 简单层的实现 本章主要讲述的是加法层(AddLayer)和乘法层(MulLayer)的实现过程。 1.加法层(AddLayer) 从正向传播和反向传播两个层面进行分析。 1).示例&#xff1a; 以zxy为对象&#xff0c;观察它的传播。zxy的导数&#xff1a;∂z/∂x1,∂z/∂…

从CNN到Transformer:基于PyTorch的遥感影像、无人机影像的地物分类、目标检测、语义分割和点云分类

我国高分辨率对地观测系统重大专项已全面启动&#xff0c;高空间、高光谱、高时间分辨率和宽地面覆盖于一体的全球天空地一体化立体对地观测网逐步形成&#xff0c;将成为保障国家安全的基础性和战略性资源。随着小卫星星座的普及&#xff0c;对地观测已具备多次以上的全球覆盖…

DVWA靶场通关和源码分析

文章目录一、Brute Force1.low2、medium3、High4、Impossible二、Command Injection1、Low2、Medium3、High三、CSRF1、Low2、Medium3、High4、Impossible四、File Inclusion1、Low2、Medium3、High五、File Upload1、Low2、Medium3、High4、Impossible六、 SQL注入1、Low2、Me…

关于catkin的一些笔记以及资料连接

大佬们早就不用catkin_make编译节点了&#xff0c;快来瞅瞅他们使用的啥 https://zhuanlan.zhihu.com/p/399753815 https://catkin-tools.readthedocs.io/en/latest/index.html# ROS 编译系统 catkin 详解 https://www.jianshu.com/p/7fccfe18d7d3 ROS学习笔记&#xff08;六…

【20230206-0209】哈希表小结

哈希表一般哈希表都是用来快速判断一个元素是否出现在集合里。哈希函数哈希碰撞--解决方法&#xff1a;拉链法和线性探测法。拉链法&#xff1a;冲突的元素都被存储在链表中线性探测法&#xff1a;一定要保证tableSize大于dataSize&#xff0c;利用哈希表中的空位解决碰撞问题。…

linux性能优化-内存buffer/cache区分

# 注意不同版本的free输出可能会有所不同 $ freetotal used free shared buff/cache available Mem: 8169348 263524 6875352 668 1030472 7611064 Swap: 0 0 0本文目的用来区分free中…

linux——守护进程守护刷抖音程序不被意外退出

先搞清楚几个概念&#xff1a;udev:设备管理工具&#xff0c;以守护进程的方式工作。位于应用层&#xff0c;主要用于监听内核硬件状态&#xff0c;它能够根据系统中的硬件设备的状态动态更新设备文件&#xff0c;包括设备文件的创建&#xff0c;删除等守护进程&#xff1a;守护…

vue 最详细教学篇(三)

文章目录vue2-cli 项目文件分析示例项目解析router-linkrouterrouter-viewmain.jspackage.jsonvue2-cli 项目 vue-cli>> 文件分析 从上图分析项目文件 1. node_modules // npm 所有下载文件包都在里面 2. public // 根目录文件, 存放index.html和一些脚本文件 3. sr…

CSDN每日一练:小桥流水人家

题目名称&#xff1a;小桥流水人家 时间限制&#xff1a;1000ms内存限制&#xff1a;256M 题目描述 在n*m的地图上&#xff0c;存在一个喷水点(x,y). 如果相邻的位置低于有水的地方&#xff0c;水就能流到相邻的某位置。 已知各个地方的海拔高度&#xff0c;求水的最大覆盖个格…

[js基础]ECMAScript2015(ES6)精要知识点(下)

模块化模块就是在单个文件中声明的JavaScript代码。我们可以用JS代码直接从其他文件中导入函数、变量和类。在NodeJS之前&#xff0c;由于没有过于复杂的开发场景&#xff0c;前端是不存在模块化的&#xff0c;后端才有模块化。NodeJS诞生之后&#xff0c;它使用CommonJS的模块…

filebrowser logo和样式自定义及免密访问

这两天接到项目一个需求&#xff0c;客户需要文件管理存储服务&#xff0c;看了下大概的功能&#xff0c;计划用源码开发的&#xff0c;但是看后期这块调整也不大&#xff0c;就采用开源的项目进行即可&#xff0c;开源项目对比后&#xff0c;发现filebrowser比较适合我&#x…

Spring如何解决循环依赖

今天面试了同程旅行&#xff0c;面试官问到了这个问题&#xff0c;所以今天来总结学习一下 Spring是如何解决循环依赖问题&#xff1f; 前言 Spring的依赖注入分为 setter注入和 构造器注入 这里说的解决循环依赖主要指的是&#xff1a;单例模式下的setter循环依赖 如果是&a…

ThreadLocal使用与原理

目录一、ThreadLocal1.ThreadLocal简介1.1 是什么2.能干嘛1.3 api介绍1.4 实战1.5 通过上面代码总结2.从阿里ThreadLocal规范开始3.ThreadLocal源码分析3.1 Thread&#xff0c;ThreadLocal&#xff0c;ThreadLocalMap 关系3.2 总结4.ThreadLocal内存泄露问题4.1 什么是内存泄漏…

PCIE 学习笔记(入门简介)

PCIE 学习笔记书到用时方恨少啊&#xff0c;一年前学PCIE的笔记&#xff0c;再拿出来瞅瞅。发到博客上&#xff0c;方便看。PCIE基础PCIE和PCI的不同PCIE采用差分信号传输&#xff0c;并且是dual-simplex传输——每条lane上有TX通道和RX通道&#xff0c;所以每条lane上的信号是…