Makefile 学习笔记
Q:为什么需要makefile
A:对大型程序来说,如果只修改了一部分文件,不应对所有源文件重新编译。而make命令可以只重新编译所有受改动影响的源文件,但是你必须要提供一个文件告诉make怎么构造,这个文件就叫makefile。
make介绍
make命令选项和参数
-k 发现错误时继续执行
-n 输出要执行的步骤,但不执行
·-f <filename> 指定makefile文件
makefile语法
依赖关系
目标名称 + 冒号 + 空格或tab + 用于创建目标文件的文件列表(用空格或tab隔开)
myapp: main.o 2.o 3.o
main.o: main.c a.h
2.o: 2.c a.h b.h
3.o: 3.c b.h c.h
表明目标myapp依赖于main.o、2.o和3.o 而main.o依赖于main.c和a.h
规则
定义目标文件的创建方式,规则所在行必须以tab开头
myapp: main.o 2.o 3.o
gcc –o myapp main.o 2.o 3.o
注释
注释以#开头,一直延续到这一行结束
Makefile中的%标记和系统通配符*的区别在于,*是应用在系统中的,%是应用在这个Makefile文件中的。
$@:目标的名字
$^:构造所需文件列表所有所有文件的名字
$<:构造所需文件列表的第一个文件的名字
$?:构造所需文件列表中更新过的文件
例如:
1 test1.o:test1.c
2 gcc -o $@ $<
$@:就是test1.o
$<:就是test1.c
1 test1.o:test1.c head.c
2 gcc -o $@ $^
$^:就是test1.c head.c
$(subst 要被替换的字符串,用来替换的字符串,被处理的字符串):
用“用来替换的字符串”替换“被处理的字符串”中的“要被替换的字符串”
所以:
$(subst .c,.o,test1.c test2.c)
就会得到test1.o test2.o
$(wildcard 寻找的文件):
在系统中寻找文件
例如:
$(wildcard *.c)
就等于找到系统中所有后缀为.c的文件,返回成以空格隔开的一整行字符
例如:test1.c test2.c test3.c 这样
$(basename 文件名):
取得文件的名字(去掉后缀的意思)
例如:
$(basename test1.c)
就会取得test1
一般我们可以使用“$(wildcard *.c)”来获取工作目录下的所有的.c文件列表。复杂一些用法;可以使用“$(patsubst %.c,%.o,$(wildcard *.c))”,首先使用“wildcard”函数获取工作目录下的.c文件列表;之后将列表中所有文件名的后缀.c替换为.o。这样我们就可以得到在当前目录可生成的.o文件列表。
推荐阅读书籍:
1.《跟我一起写Makefile》
2.《Managing Projects with GNU Make》
参考资料: