首页
Web开发
Windows程序
编程语言
数据库
移动开发
系统相关
微信
其他好文
会员
首页
>
编程语言
> 详细
C语言中宏定义使用方法详解
时间:
2014-09-20 23:23:49
阅读:
830
评论:
0
收藏:
0
[点我收藏+]
标签:
宏定义
替换方法
#
##
C语言中的宏替换详解
首先看一个问题:
#include <stdio.h>
#define PRINT_CLINE() printf("%d", ______)
int main(void)
{
PRINT_CLINE();
PRINT_CLINE();
return 0;
}
在横线处填上适当的代码,使得上面这段代码的输出为34。
我想一般人看到这个问题的时候头脑里都没有明确的思路来解答这个它。我看到这个问题的时候想出了各种办法来解答它,最终还是没有通过编译器的检查,比如我想过的其中一个办法是:
(int static i=2, i++)
想着在这个位置定义一个static变量,并且赋上初值为2,最后在加上一个i++,根据逗号运算符的运算规则,整个表达式的值应该是最后一项的值,想法确实很完美,但是这样是通不过编译器的!在这个位置使用一条定义变量的语句是不合法的!想了很久实在想不出来办法了。于是重新整理了宏定义的使用方法,终于找到了答案。下面一步步来说宏定义的使用方法:
1.最简单的替换
#defind Pi 3.14159
上面的这条语句就是比较常用的简单替换了,在预处理阶段,程序代码中出现Pi的地方都被替换为后面的3.14159。
2.带参数的宏替换
#define MAX(a, b) (a)>(b)?(a):(b)
这个就是带参数的宏替换了,在代码中使用MAX宏的时候,括号内部的参数会跟随到宏替换中。当然这个替换需要注意的地方就是记得为每个参数加上(),不然可能会产生边际效应。
3.字符替换符:#@
先看下面的这段代码:
#include <stdio.h>
#define PT_CHAR(x) printf("%c", #@x);
int main(void)
{
PT_CHAR(d);
return 0;
}
程序的输出为d。或许你会问,那直接将宏定义中的#@x用x替换掉不就可以了么,粗略的一看这样的说法确实是可以的,但是宏替换的时候PT_CHAR(d)编译器会认为d是一个传递的参数,既然d并非一个常量,那么编译器就只好认为它是一个变量了,但是这样的话问题就出来了,d并没有定义过!
4.字符串宏替换符:#
这个跟上面的有点类似了,比如下面的两行代码片段:
#define PT_STRING(x) printf("%s", #x)
PT_STRING(Hello!);
如果想要达到输出为Hello!的目的,就要使用#x,如果不使用的话根据前面的分析,编译器会把Hello!整体理解为一个变量,但是即便这样理解的话,这个!也是不能作为变量的一部分的啊,所以编译器会报出比较多的错误。
5.连接宏替换符:##
#define p(n) printf("symbol"#n"=%d", symbol##n)
int symbol9 = 9;
p(9);
上面的输出为symbol9=9,symbol##n将symbol和n(也就是传递过来的9)连接起来,构成了变量symbol9。
6.ANSI标准中的几个标准预定义宏
__LINE__:在源代码中插入当前源代码行号;
__FILE__:在源文件中插入当前源文件名;
__DATE__:在源文件中插入当前的编译日期
__TIME__:在源文件中插入当前编译时间;
__STDC__:当要求程序严格遵循ANSI C标准时该标识被赋值为1;
__cplusplus:当编写C++程序时该标识符被定义。
看到这里,上面的问题答案也就出来了,标准预定义宏中的__LINE__代表了源代码在改代码中的行号,使用这个宏就可以很方便的实现上面的功能了。
答案:#define PRINT_CLINE() printf("%d", __LINE__-4)
C语言中宏定义使用方法详解
标签:
宏定义
替换方法
#
##
原文地址:http://blog.csdn.net/laoniu_c/article/details/39435981
踩
(
0
)
赞
(
0
)
举报
评论
一句话评论(
0
)
登录后才能评论!
分享档案
更多>
2021年07月29日 (22)
2021年07月28日 (40)
2021年07月27日 (32)
2021年07月26日 (79)
2021年07月23日 (29)
2021年07月22日 (30)
2021年07月21日 (42)
2021年07月20日 (16)
2021年07月19日 (90)
2021年07月16日 (35)
周排行
更多
Spring Cloud 从入门到精通(一)Nacos 服务中心初探
2021-07-29
基础的排序算法
2021-07-29
SpringBoot|常用配置介绍
2021-07-29
关于 .NET 与 JAVA 在 JIT 编译上的一些差异
2021-07-29
C语言常用函数-toupper()将字符转换为大写英文字母函数
2021-07-29
《手把手教你》系列技巧篇(十)-java+ selenium自动化测试-元素定位大法之By class name(详细教程)
2021-07-28
4-1 YAML配置文件 注入 JavaBean中
2021-07-28
【python】 用来将对象持久化的 pickle 模块
2021-07-28
马拉车算法
2021-07-28
用Python进行冒泡排序
2021-07-28
友情链接
兰亭集智
国之画
百度统计
站长统计
阿里云
chrome插件
新版天听网
关于我们
-
联系我们
-
留言反馈
© 2014
mamicode.com
版权所有 联系我们:gaon5@hotmail.com
迷上了代码!