1. Makefile中:=, =, ?=和+=
“=”是最普通的等號,在Makefile中也是最容易搞錯的賦值等號,使用“=”進行賦值,變量的值是整個makefile中最後被指定的值。
舉例如下:
x = A
y = $(x) B
x = AA
經過上面的賦值後,最後y的值是AA B,而不是A B。make會將整個makefile展開後,再決定變量的值。也就是說,變量的值將會是整個makefile中最後被指定的值。
“:=”表示直接賦值,賦予當前位置的值,變量的值決定於它在makefile中的位置,而不是整個makefile展開後的最終值。
舉例如下:
x := A
y := $(x) B
x := AA
經過上面的賦值後,最後y的值是A B,即根據當前位置進行賦值。相比於"=",":="纔是真正意義上的直接賦值。
"?="表示如果該變量沒有被賦值,則賦予等號後的值
x ?= A
如果x在之前沒有被賦值,那麼x的值就爲A
x = B
x ?= A
這種情況下,x的值就是B
“+=”和我們平時寫代碼的理解是一樣的,表示將等號後面的值添加到前面的變量上
x = A
x += B
x的值是A B
2. Makefile中$^,$@,$?和$<
$^ 表示所有的依賴文件,以空格分隔。如果依賴文件中有重複,那麼這個變量會去除重複文件,只保留一份
$@ 表示目標文件
$< 表示第一個依賴文件
$? 表示比目標還要新的依賴文件列表
舉例如下,目錄中有這些文件
$ ls
hello.c world.c main.c Makefile
Makefile文件如下:
main: main.o hello.o world.o
gcc -o main main.o hello.o world.o
main.o: main.c
cc -c main.c
hello.o: hello.c
cc -c hello.c
world.o: world.c
cc -c world.c
clean:
rm *.o
rm main
改爲用上述符號進行替代後,Makefile文件如下:
main: main.o hello.o world.o
gcc -o $@ $^
main.o: main.c
cc -c $<
hello.o: hello.c
cc -c $<
world.o: world.c
cc -c $<
clean:
rm *.o
rm main
下面的命令表示把有更新的依賴文件重新打包到庫lib中, 如果只有hello.o更新,則$?代表hello.o, 如果hello.o world.o都有更新,則$?代表hello.o world.o的集合。
lib : main.o hello.o world.o
ar r lib $?