https://blog.csdn.net/qq_41071068/article/details/92805050
类对象宏(无参宏), 即宏名之后不带参数,只是简单的文本替换
其定义的一般形式为:
#define 标识符 字符串
#define N 10
类函数宏(带参数的宏)
C/C++允许宏带有参数。
带参数的宏定义,宏名中不能有空格,宏名与形参表之间也不能有空格,而形参表中形参之间可以有空格, 在行末不必加分号,如加上分号则在预处理时连分号也一起添加到代码中。
约定 : 一般来说函数和类函数宏使用语法很相近, 所以语言本身无法帮我们区分二者, 那我们平时的一个习惯是:
把宏名全部大写 函数名不要全部大写
#define A2(a,b) (a)+(b)
#define A3(a,b) ((a)+(b))
类函数宏还可以定义多个语句
注意: 如果宏定义太长, 可以分成几行书写, 除了最后一行外, 其余每行都在末尾加上 \ (反斜杠)(续行符)
#define PRINT_1(a,b) \
printf(#a"+"#b"=%d\n",(a)+(b))
#define SUM_PRINT(x,y,z) x##y += z;\
printf(#x#y"=%d\n",x##y)
代码中用到了#与##, 分别是啥意思呢
#
的作用
把一个宏参数变成对应的字符串
##
的作用
##可以把位于##两边的字符(串)合成一个符号, 这样的操作必须产生一个合法的标识符,否则是无意义的, 结果是未定义的, 就如上面的代码中a和b(a##b)形成了新的标识符ab, ab是我们事先定义的, 所以有意义且正确
类函数宏(带参数的宏)和函数的对比
类函数宏通常用于一些简单的运算, 比如说在两个数中找出最大或最小的一个
#define MAX(a,b) ((a)>(b)?(a):(b))
那为什么不用函数来完成这个任务?
原因有二:
- 调用函数(需要开辟内存,释放内存等)可能比执行这个带参数的宏(插入一小段代码)进行小型计算所需要的时间更多。所以宏比函数在程序的规模和速度方面更胜一筹。
- 更为重要的是函数的参数必须声明为特定的类型。所以函数只能在类型合适的表达式上使用。反之这个宏可以适用于整形、长整型、浮点型等可以用于大小比较的类型。宏是类型无关的。
当然和宏相比函数也有劣势的地方:
- 每次使用宏的时候,一个宏定义的代码将插入到程序中。除非宏比较短,否则可能大幅度增加程序的长度。
- 宏是不方便调试的。
- 宏由于类型无关,也就不够严谨。
- 宏可能会带来运算符优先级的问题,导致程容易出现错。
宏有时候还可以做函数做不到的事情。比如:宏的参数可以出现类型,但是函数做不到。