C语言宏定义与条件编译

目录

一、定义一个标准宏

二、带未知数的宏定义

三、宏在哪里可以定义

四、何时进行宏替换

五、宏的有效范围 

六、宏定义多语句

 七、undefine取消宏

 八、宏中的# 与 ##

九、条件编译


一、定义一个标准宏

#define MAX_LEN 10

  1. 允许留有空格,但请不要写成下面这样,这看着很不舒服
  2. 宏的名字建议全部大写,单词与单词之间用 _ 连接,这是一个很好的规范
  3. 最后不要加分号

二、带未知数的宏定义

# define SUM(x)   (x)+(x)
int main()
{
    printf("%d\n", SUM(10));
    printf("SUM(20)\n");
    return 0;
}

编译器会将SUM(x),进行简单的宏替换,不会自动给加括号等 !!!

还是用上面的宏,这个结果会是什么呢

printf("%d\n", SUM(10)*2);         // 输出30     替换为10+10*2

三、宏在哪里可以定义

结论:并非要在开头,哪里都可以定义宏,无论是函数里,函数外,代码快里等等

#define OUT_DEF 10
int main() {
#define IN_DEF 20
    printf("%d %d", OUT_DEF, IN_DEF);
    return 0;
}

四、何时进行宏替换

一份C语言代码变为可执行程序的四个步骤

  • 预处理:去注释、宏替换、条件编译 (去注释先于宏替换)
  • 编译:将C语言转为汇编语言
  • 汇编:汇编语言转为二进制文件(不可被执行)
  • 链接:自身文件与库文件关联,形成可执行程序          

不要企图用宏充当注释,因为去注释先于宏替换,相当于你定义了一个为空的宏

#define NO_EXE //

五、宏的有效范围 

结论:从宏定义处开始,只对他下面的代码起作用

 因为函数调用是在编译时进行的而宏替换是在预处理阶段

当宏替换时还没解释show函数,编译器编译时不认识M

六、宏定义多语句

结论:用do{}while(0)封装。为什么呢?

#define INTI_RECT_VALUE(a, b) \
do{\
    printf("before:%d %d\n", a, b);\
    a=0;\
    b=0;\
    printf("after:%d %d\n", a, b);\
}while(0)

1.该宏在if,while结构中,只有一条语句,没加{ },报错

2.加了{ },最后会多一个分号,报错

当然现在的编译器都很强大可能给你自动优化

 七、undefine取消宏

#define NUM 10

#undefine NUM

看题:

//程序输出结果
#define X 10
#define Y X+10
#undef X
#define X 20
int main() {
    int x = Y;
    printf("%d\n", x);
    return 0;
} 
// 输出30

宏就是简单的替换,Y替换为X+10,X替换为20

 八、宏中的# 与 ##

结论:

#可将s里的内容转为字符串

##用于构建新符号

看两段代码

#define STR(s) #s	//将s的内容替换为字符串
int main()
{
	printf("Pi:"STR(3.14)"\n");
	return 0;
}
#define TOSTRING(s) #s
int main()
{
	int a = 124;
	char *s = TOSTRING(a);
	printf(s);    // 输出a
	return 0;
}

代码一输出字符串“3.14”,代码二输出字符‘a’ 宏替换先于编译

 ## 构建新符号

#define XNAME(n) student##n
int main() {
	XNAME(1);	//替换为student1;
	return 0;
}

九、条件编译

#ifdef 与 #if

  • #ifdef:检查宏是否被定义
  • #if:检查宏的结果是真是假
  • 条件编译用于裁剪代码,降低维护成本,例如一个软件企业版与社区版

1.  #ifdef …… #else……#endif (不常用)

//条件编译 #ifdef检查宏是否被定义
//这叫定义
#define M
int main()
{
#ifdef M
	printf("M is define\n");
#else
	printf("M is not define\n");
#endif
	return 0;
}

2.  #if……#else……#endif (常用)

     不定义走else,不赋值报错

#define M 1
int main()
{
#if M
	printf("M is true define\n");
#else
	printf("M is false define\n");
#endif
	return 0;
}

  • #ifdef可以被#if define()替换
  • #ifndef可以被#if !define()替换 
  • 支持多条件判定
#define C
#define CPP
int main()
{
#if (defined(C) && defined(CPP))
	printf("C and CPP\n");
#else
	printf("other\n");
#endif
	return 0;
}

支持嵌套

#define C
#define CPP
int main()
{
#if defined(C)
	#if defined(CPP)
		printf("CPP\n");
	#endif
	printf("C\n");
#else
	printf("other\n");
#endif
	return 0;
}

欢迎大家指正!!!

  • 4
    点赞
  • 7
    收藏
    觉得还不错? 一键收藏
  • 打赏
    打赏
  • 2
    评论
评论 2
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包

打赏作者

不会就选C.

你的鼓励将是我创作的最大动力

¥1 ¥2 ¥4 ¥6 ¥10 ¥20
扫码支付:¥1
获取中
扫码支付

您的余额不足,请更换扫码支付或充值

打赏作者

实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值