C语言补充-分文件编程和条件编译
:D
C语言的编译过程
从.c文件得到.exe文件大体上分为以下三个步骤:
- 预处理
- 编译
- 链接
预处理是指进行一些复制粘贴操作,比如#include
"..."
的文件复制粘贴,还有宏的展开
编译是指把预处理得到的暂时的.c文件编译为二进制文件,编译之后生成.o
文件
链接是指把多个编译得到的源文件和系统组件(我也不知道是什么)全都打包起来,形成可执行文件
gcc基本用法
gcc是一个编译器+链接器(但是我们通常称它为编译器
命令gcc --help
为显示帮助,可以快速查询各选项的功能
命令格式:
1 | gcc [选项] [文件名] |
下面是gcc常用的选项
-o
gcc test.c -o test
设置输出的文件为test.exe
(如果不设置,默认a.exe)-c
仅编译,不链接
例如
gcc -c test.c
输出test.o文件-S
gcc -S test.c
汇编
-E
预处理
直接
gcc -E test.c
似乎会把结果输出到终端,要输出到文件应该用gcc -E test.c -o test.i
-I
指定头文件地址(如果头文件不在当前文件夹里面就需要用这个
-O1 -O2 -O3
编译优化
分文件编程
使用gcc实现
有一个主文件,包含 main函数
如果要将其它函数的实现写在其他文件中,需要一个头文件function.h
头文件里面写函数的声明,和头文件这个名字相同的.c
文件(function.c)里面写函数的实现。
编译有两种方法
直接一次性编译全部文件生成可执行文件
1
gcc [所有.c文件]
选择.c文件的时候支持通配符,比如要编译这个文件夹里所有的
*.c
文件可以1
gcc *.c
先编译单个文件再链接
这样做的好处是当修改了多个文件中的一个时,其他文件不必重新编译,适用于文件较多的情况。
预处理命令
以下是一些常用的预处理命令,用来控制哪些代码参加编译,哪些不参加
#define
#undef 取消定义,因此这个宏的作用域在#define和#undef之间
#ifdef
#ifndef if not define
#if
#elif
#else
#endif
defined
用法:
1
#if defined(关键字)
这么看似乎和#ifdef没啥区别,但是这个可以用来判断多个条件(用&&,||连接),并且可以用在#elif 后面
if-elseif-else-endif:
1 |
|
#ifndef
用法类似
实用的例子
目前都是写一些小代码,对我来说实用一些的就只有这个了吧:
写代码调试的时候,如果要输出中间结果经常会把代码改的乱七八糟,提交的时候删起来比较麻烦,但是如果把输出中间结果的代码写到条件编译里面,例如:
1 |
|
而在调试的时候编译加上选项-DDEBUG
:
1 | gcc -DDEBUG test.c |
就相当于在代码里面定义了DEBUG
(上面的"DEBUG"可以换成任何单词)
[参考资料]
[1] C语言中.h和.c文件解析
[2] GCC 编译命令