Make¶
Make 是 Unix 系统上历史悠久的构建系统,使用的构建文件叫 Makefile,用户可以指定不同的编译目标以及指定它们的相关依赖,Make 会自动构建目标所需要的依赖文件,同时会分析哪一些依赖是可以不用重新构建的,实现增量构建,加速构建过程。
许多其他的构建系统或多或少都是对 Make 的一个改进,掌握 Make 的基本概念,就很容易学习其他构建系统了。
阅读建议
如果你赶时间,或者是在 Windows 上开发,那么可以暂时跳过本节,直接看 CMake,这是一个跨平台的元构建系统,而且使用了更简单也更高层级的描述语言,使用它的前提知识仅需要掌握程序的编译与链接。
基础概念¶
构建系统中的基本元素只有三个:目标、依赖以及构建目标的指令。
目标很好理解,例如我们想生成一个叫 hello
的可执行程序,那么 hello
就是一个目标,如果想生成一个叫 mylib
的库,那么 mylib
也是一个目标。
依赖同样很好理解,就是一个目标要生成的话,有什么东西是必须得先构建出来的。而依赖本身也是目标,也可以是文件。例如,生成 hello
之前需要先生成 mylib
用来链接,那么 mylib
就是 hello
的一个依赖。而 mylib
的依赖可能是 mylib.cpp
和 mylib.h
。如果我们画一个图,所有的目标作为节点,存在依赖关系的目标之间,画一条从被依赖的目标指向依赖它的目标的箭头,就得到了一张有向图。如果这个有向图有环的话,就会有循环依赖的问题,没有办法构建。而如果这个图无环,那么就可以使用拓扑排序的方法,不断进行构建,最终得到编译产物。两个目标没有依赖的话,是可以并行构建的,这也是使用构建系统能加速构建的一个原因。
而构建目标的指令如字面意思,就是我们应该怎么生成一个产物,例如 g++ hello.cpp
。
Makefile 格式¶
Makefile 中对于上面三个元素的描述如下:
目标: 依赖1 依赖2 ...
构建指令1
构建指令2
...
由于历史原因,构建指令前的缩进必须使用 Tab,也就是 \t
。