2. 自动变量
在 Makefile 的每个规则的命令中都可以使用 自动变量 来代替目标文件、依赖文件列表、单个的依赖文件等特殊的变量。这些变量称之为自动变量。
自动变量可以 Makefile 更加简洁,通用。
Makefile 的自动变量如下表所示:
自动变量
说明
$@目标文件名。
$<第一个依赖文件名。
$^所有依赖文件名(去掉重复项)。
$+所有依赖文件名,保持原依赖列表(包含重复项)。
$?比目标文件新的所有的依赖文件名。
$*通配符匹配的部分。
$%档案成员名 。
示例:
现在有如下的 C 语言的源代码程序,我们需要将其编译成一个应用程序 myapp。
myapp/
├── file1.c
├── file1.h
├── file2.c
├── file2.h
└── main.c
文件内容如下:
// filename: file1.h
#ifndef __FILE1_H
#define __FILE1_H
void myfunc1(void);
#endif // __FILE1_H
// filename: file1.c
#include <stdio.h>
#include "file1.h"
void myfunc1(void) {
printf("库函数 myfunc1 被调用\n");
}
// filename: file2.h
#ifndef __FILE2_H
#define __FILE2_H
void myfunc2(void);
#endif // __FILE2_H
// filename: file2.c
#include <stdio.h>
#include "file2.h"
void myfunc2(void) {
printf("库函数 myfunc2 被调用\n");
}
// filename: main.c
#include "file1.h"
#include "file2.h"
int main(int argc, char * argv[]) {
// 调用合作方的库函数
myfunc1();
myfunc2();
return 0;
}
上述文件编译的过程如下:
+---------+ +---------+
| file1.h | --> | file1.o | -->.
+---------+ +---------+ |
|
+---------+ +---------+ | +-------+
| file2.c | --> | file2.o | ---+------> | myapp |
+---------+ +---------+ | +-------+
|
+---------+ +---------+ |
| main.c | --> | main.o | -->`
+---------+ +---------+
编写 Makefile 如下:
.PHONY: all clean
SOURCES := file1.c file2.c main.c
HEADERS := file1.h file2.h
OBJECTS := file1.o file2.o main.o
TARGET := myapp
all: $(TARGET) # 编译最终目标
$(TARGET) : $(OBJECTS)
gcc -o $@ $^
main.o : main.c $(HEADERS)
gcc -o $@ -c $<
file1.o : file1.c $(HEADERS)
gcc -o $@ -c $<
file2.o : file2.c $(HEADERS)
gcc -o $@ -c $<
clean: # 清除目标文件
rm $(OBJECTS)
编译和运行结果如下:
weimingze@mzstudio:~/myapp$ make
gcc -o file1.o -c file1.c
gcc -o file2.o -c file2.c
gcc -o main.o -c main.c
gcc -o myapp file1.o file2.o main.o
weimingze@mzstudio:~/myapp$ ./myapp
库函数 myfunc1 被调用
库函数 myfunc2 被调用
在上述 Makefile 的规则中,我们使用 $@ 代替目标,$< 代替依赖的第一个文件,$^ 代替依赖列表中的所有文件。
实验:
使用上述示例程序中的五个文件,修改 Makefile 如下,运行此 Makefile,查看打印结果是什么?为什么?
all: main.c file1.c file2.c file1.h file2.h main.c
echo $@
echo $<
echo $^
echo $+