第7课 - 变量的高级主题(下)
1. makefile中的环境变量(全局变量)
(1)makefile中使用系统环境变量
makefile中可以直接使用系统中的环境变量(系统环境变量的本质就是全局的键值对)
-
如果 makefile 中定义了同名变量,那么环境变量将会被覆盖
-
运行 make 时指定 "-e" 选项,优先使用环境变量
编程实验:
1 # 测试makefile中环境变量的使用
2
3 # 例1
4 PATH := my path
5
6 test :
7 @echo "PATH => $(PATH)"
8
9 #输出结果: my path
10
11 # 例2
12 test :
13 @echo "PATH => $(PATH)"
14
15 # 输出结果 /usr/local/sbin:/usr/local/bin:/usr/sbin:/usr/bin:/sbin:/bin:/usr/games:/usr/local/games
16
17 # 例3
18 PATH := my path
19
20 test :
21 @echo "PATH => $(PATH)"
22
23 # 执行 make 时添加 -e 选项
24 # 输出结果:/usr/local/sbin:/usr/local/bin:/usr/sbin:/usr/bin:/sbin:/bin:/usr/games:/usr/local/games
(2)为什么要在makefile中使用环境变量?
— 优势:环境变量可以在所有 makefile 中使用
— 劣势:过多的依赖于环境变量会导致移植性降低
(3)变量在不同makefile之间的传递方式:3种
— 直接使用系统中的环境变量(不推荐,太依赖于系统)
— 使用 export 定义环境变量进行传递(定义临时的环境变量)
— 定义 make 命令行变量进行传递(推荐)
1 # makefile 演示变量在不同 makefile 之间的传递方式 2 3 # makefile文件 4 5 HOME := my home 6 var := swj 7 8 test : 9 @echo "HOME => $(HOME)" 10 @echo "var => $(var)" 11 @echo "make another file ..." 12 @$(MAKE) -f makefile.1 13 14 # makefile.1文件 15 16 test : 17 @echo "HOME => $(HOME)" 18 @echo "var => $(var)" 19 20 # 输出结果: 21 HOME => my home 22 var => swj 23 make another file ... 24 make[1]: 正在进入目录 `/home/swj/12-plan/makefile/lesson-7' 25 HOME => my home 26 var => 27 make[1]:正在离开目录 `/home/swj/12-plan/makefile/lesson-7'
— 该例说明的问题:
-
makefile中定义环境变量会把系统中该环境变量的值覆盖
-
在makefile中定义的变量只具有 "文件作用域" ,在makefile.1中不能使用
— 遇到的坑:
由于我的ubuntu没有安装Java,没有使用JAVA_HOME这个环境变量,使用的是PATH环境变量,PATH := my path ,导致后面调用make出现错误。原因是由于make是一个进程,它会复制系统的一份环境变量来使用,复制的环境变量作用域是 "进程域", 上面 PATH := my path 就把该环境变量的值更改了,导致后面调用make时出现 "找不到命令" 的错误。环境变量之间的关系如下图所示。
1 # 演示 export 和 命令行传递变量给其它makefile 2 3 # makefile 文件 4 HOME := my home 5 export var := swj 6 new := cool 7 8 test : 9 @echo "HOME => $(HOME)" 10 @echo "var => $(var)" 11 @echo "make another file ..." 12 @$(MAKE) -f makefile.1 13 @$(MAKE) -f makefile.1 new:=$(new) 14 15 # makefile1 文件 16 test : 17 @echo "HOME => $(HOME)" 18 @echo "var => $(var)" 19 @echo "new => $(new)" 20 21 # 输出结果: 22 HOME => my home 23 var => swj 24 make another file ... 25 make[1]: 正在进入目录 `/home/swj/12-plan/makefile/lesson-7' 26 HOME => my home 27 var => swj 28 new => 29 make[1]:正在离开目录 `/home/swj/12-plan/makefile/lesson-7' 30 make[1]: 正在进入目录 `/home/swj/12-plan/makefile/lesson-7' 31 HOME => my home 32 var => swj 33 new => cool 34 make[1]:正在离开目录 `/home/swj/12-plan/makefile/lesson-7'
2. makefile中的局部变量
(1)目标变量(局部变量)
— 作用域只在指定目标及连带规则中
-
-
target : name<assignment>value
-
target : override name<assignment>value
-
1 # 测试目标变量的使用 2 3 var := swj 4 test : var := test-var 5 6 test : 7 @echo "var => $(var)" 8 9 # 输出结果:var => test-var
(2)模式变量
— 模式变量是目标变量的扩展
— 作用域只在符合模式的目标及连带规则中
-
-
pattern : name <assignment> value
-
pattern : override name <assignment> value
-
1 # 测试模式变量的使用 2 3 var := swj 4 %t : var := test-var 5 6 test : 7 @echo "var => $(var)" 8 9 another : 10 @echo "var => $(var)" 11 12 # 输出结果 13 var => test-var 14 var => swj
3. 小结:makefile中的三种变量类型
(1)全局变量:makefile 外部定义的环境变量,不同的makefile之间可以传递。
(2)文件变量:makefile 中定义的变量,作用域在当前文件中。
(3)局部变量:指定目标的变量,作用域在目标中。