C语言预处理

代实现执行需要通过两个大体的过程

1.第一是翻译,把你敲的代码转换成机器的可执行指令

2.第二就是运行,机器执行由代码转换过来的指令

1.编译与链接

程序通常包括多个源文件,这些文件需要单独通过编译器转换成目标文件

  • 转换成目标文件之后再由链接器捆绑在一起之后形成可执行程序

  • 链接器还会将代码中所引用的头文件链接到程序中

1.1编译本身也分为几个阶段

  1. 删除注释

  1. 处理预处理指令#include等等

  1. 符号汇总

  1. 转换成机器指令

关于符号汇总,就是将各个文件中的关键字汇总,比如函数,全局变量

1.2链接

  • 合并段表

  • 合并符号表和符号表的重定位

关于合并符号表,编译器会将各个文件生成的符号表进行合并,将其中重复的符号进行合并,如果合并符号表中后仍然存在地址无效的关键字,编译器将会报错(此情况原因可能是因为一个函数被声明了但是没有被定义)。

2.预处理详解

2.1预定义符号

__FILE__

__LINE__

__DATE__

__TIME__

__STDC__

//进行编译的源文件

//文件当前的行号

//文件被编译的日期

//文件被编译的时间

//如果编译器遵循ANSI C,其值为1,否则未定义

这些符号都是c语言内置的

2.2#define

在使用#define定义宏的时候需要注意几个点

  • 在使用宏是是直接替换的,并不会计算出结果之后再替换

#define X 1+2

int main()

{

int sum=2*X;

}

如果不够细心的话计算出的sum的结果是6

而在编译器眼中这段代码是这个样子的

#define X 1+2

int main()

{

int sum=2*1+2;

}

结果就是4了

可以在定义的时候多带几个括号,就尽可能避免这种问题

#define X (1+2)

int main()

{

int sum=2*(1+2);

}

在定义带参数的宏时候也是同理

  • 在定义宏的时候不要带上;否则可能会引起语法问题

2.2.3#define中#和##的作用

在字符串中插入“#参数”可以将变量名转换成字符串并插入到字符串中

#define PRINT(X) printf("这个"#X"大小是%d",x)

int main()

{

int a=10;

PRINT(a);

}

##的作用是将两边的符号合并成一个符号

#define ADD(a,b) a##b+=10

这段代码的作用是把ab加上10,但是ab如果没有定义的话是会报错的

2.3预处理指令

2.3.4#undef

这条指令用于移除一个宏定义。

#undef NAME

//如果现存的一个名字需要被重新定义,那么它的旧名字首先要被移除。

2.4条件编译

有的时候为了避免重复定义符号或者避免重复引入头文件,但是又不知道在之前的代码中有没有定义,可以在定义符号和引入头文件的时候使用条件编译指令。

  • #if(常量表达式)

  • #else

  • #endif

判断是否被定义

#if defined(symbol)

  • 0
    点赞
  • 0
    收藏
    觉得还不错? 一键收藏
  • 0
    评论

“相关推荐”对你有帮助么?

  • 非常没帮助
  • 没帮助
  • 一般
  • 有帮助
  • 非常有帮助
提交
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

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

余额充值