在Python中,你执行一个程序只需要输入Python和你想要执行的程序代码。Python解释器会运行它们,并且在执行过程中会导入一些其他的库和你需要的东西。C语言是完全不同的,你必须编译你的源代码,手动链接成一个可执行的二进制文件。手动做这些事情是痛苦的,在上一个练习中你仅仅是执行make命令就行了。
在本次练习中,你将得到一个GNU make的速成教程,学习使用make是你学习C语言的一部分。Make将会像你的Python脚本一样,成为本书的重要部分。它能够构建你的代码,运行测试,设置 一些东西,为你做所有的事情就像Python通常做得一样。
不同的是,我将会向你展示Makefile
的魔力,它将解决你在C程序构建过程中很多烦杂愚蠢的琐事。在本次练习中不会涉及过些,在你掌握了make的一些基础之后,我会向你展示更多make的能力。
使用make的第一阶段就是使用它构建程序。Make能够实现各种复杂的功能操作,构建各种各样的文件。在上次练习中你已经使用过如下命令:
$ make ex1
# 或者是下面这行命令
$ CFLAGS="-Wall" make ex1
第一行命令,你告诉make“我要创建一个名为ex1
的文件”,Make会执行如下的操作:
- 判断
ex1
文件是否存在? - 不存在,好,判断是否有一个文件以
ex1
开头? - 有,并且是
ex1.c
文件。我是否知道如何构建.c
文件? - 知道,我会运行
cc ex1.c -o ex1
来构建他们。 - 我将会使用
cc
命令把ex1.c
编译成ex1
。
上面列出的第二个命令,用一种给make命令传递修饰参数的方式。如果你不熟悉Unix shell是如何工作的,你可以设置一个影响程序运行的“环境变量”。你可以使用命令 export CFLAGS="-Wall"
,你也可以把它们放到你的命令前去运行,并且这个环境变量只有在程序运行时才设置。
在这个例子当中,我使用这个命令CFLAGS="-Wall" make ex1
,所以它给会cc
命令添加一个参数-Wall
。这个参数告诉cc
编译器反馈所有警告信息(实际上是不可能打印出所有的警告信息)。
像上面那种方式使用make命令实际上是非常不优雅的,我们现在开始使用Makefile
以至于你能更好理解make。首先,创建一个文件,输入以下内容:
CFLAGS=-Wall -g
clean:
rm -f ex1
在当前目录保存文件,并命名为Makefile
。Make会自动默认有一个叫Makefile
的文件,只需在当前目录运行make命令。注意:确保你在些文件中只输入了TAB字符,不要混合TAB和空格。
Makefile
文件定义了一些新的东西。首先在文件中我们设置了CFLAGS
,所以我们不再需要一直设置此参数,同时添加了-g
标识用来debug。然后我们有一个叫clean
的部分,它告诉make如何去清理我们的小项目。
确保Makefile
和ex1.c
文件在同一个目录,然后运行如下命令:
$ make clean
$ make ex1
如果以上运行正常,你会看到如下输出:
$ make clean
rm -f ex1
$ make ex1
cc -Wall -g ex1.c -o ex1
ex1.c: In function 'main':
ex1.c:3: warning: implicit declaration of function 'puts'
从这里我们可以看到,我们运行make clean
它告诉make去执行我们的clean
目标。再加去看Makefile
文件,你会发现在clean
缩进的地方,我放置了一条shell命令让make去执行。如果你有需要,你可以放很多命令在这个地方,所以它是一个非常强大的自动化工具。
同时注意到,即使我们在Makefile
文件中没有提到ex1
,make
仍然知道如何构建并使用我们的特殊设置。
以上的内容作为开始已经足够了,但先让我们对Makefile
文件作一些特殊的修改,你再看看会发生什么。在rm -f ex1
这一行取消缩进你看看会发生什么。再运行make clean
你会看到如下输出:
$make clean
Makefile:4: *** missing separator. Stop.
请始终记得缩进,如果你看到类似这种奇怪的错误,一般情况请仔细检查你使用的制表符,因为一些make
程序对这些是非常挑剔的。
- 创建一个
all: ex1
的目标,这样你构建ex1
只需要执行make
命令 - 阅读
man make
的内容,你会学到一些如何运行它的知识 - 阅读
man cc
的内容,找到-Wall
和-g
相关的信息 - 研究一些线上的Makefiles文件,看你是否能改善它
- 在另一个项目叫找到
Makefile
文件,尝试去理解它在做什么