Makefile学习笔记_04_变量定义与使用_常用符号

目录

说明

自学B站某课程的笔记,欢迎小伙伴们共同讨论,若有理解不对的地方也欢迎指出。
https://www.bilibili.com/video/BV1EM41177s1/spm_id_from=333.999.0.0
开发环境:Visual Studio Code + gcc

变量的定义/声明

变量名 := 文件夹名/文件名
cpp := src/main.cpp
obj := objs/main.o

Note: 这里的 src/main.cpp 和 objs/main.o 只是字符串,并不代表真的存在文件。后续示例中会说明,比如我们要用 cpp 生成 obj ,那么 cpp 表示的 main.cpp 文件必须存在,而 obj 表示的 main.o 文件是我们即将通过编译生成的文件,并不存在。

变量的引用

$(变量名) 美刀+圆括号
${变量名} 美刀+花括号

示例

我们通过src文件夹下的main.cpp文件编译生成objs文件夹下的main.o文件。其中,srcobjs为同级目录下的文件夹,obj为空文件夹。
在这里插入图片描述
代码如下:

cpp := src/main.cpp  #定义变量cpp
obj := objs/main.o   #定义变量obj

$(obj) : ${cpp}      #引用变量 obj,其中 obj 的依赖是变量 cpp,即 main.o 的依赖是 main.cpp
	@g++ -c $(cpp) -o $(obj)
#g++ -c src/main.cpp -o objs/main.o

compile: $(obj)   #编译目标obj变量

debug:
	@echo $(cpp)  #输出变量cpp
	@echo $(obj)  #输出变量obj

我们可以先通过make debug命令输出cppobj两个变量,观测其结果是否正常。
在这里插入图片描述
结果显示输出两个字符串,正常。
然后,通过make compile命令进行编译,编译完成后,空文件夹objs下会出现main.o文件。
在这里插入图片描述

解释: 以下两段代码是同样的意思,只不过一个是直接通过文件夹/文件名的方式在编译,而另一个是把“文件夹/文件名”这个字符串定义成变量,然后再通过变量来编译。

$(obj) : ${cpp}      #引用变量 obj,其中 obj 的依赖是变量 cpp,即 main.o 的依赖是 main.cpp
	@g++ -c $(cpp) -o $(obj)
g++ -c src/main.cpp -o objs/main.o

完善上述代码后,完整代码如下:

cpp := src/main.cpp  #定义变量cpp
obj := objs/main.o   #定义变量obj

$(obj) : ${cpp}      #引用变量 obj,其中 obj 的依赖是变量 cpp,即 main.o 的依赖是 main.cpp
	@g++ -c $(cpp) -o $(obj)
#g++ -c src/main.cpp -o objs/main.o

compile: $(obj)   #编译目标obj变量

clean:            #删除objs文件夹
	@rm -rf objs
	
debug:
	@echo $(cpp)  #输出变量cpp
	@echo $(obj)  #输出变量obj
	
.PHONY: clean debug #避免目标与文件夹同名,申明为伪目标。

预定义变量

可以用于替换一些目标以及文件的名字。

  • $@: 目标(target)的完整名称
  • $<: 第一个依赖文件(prerequisties)的名称
  • $^: 所有的依赖文件(prerequisties),以空格分开,不包含重复的依赖文件

通过预定义变量,可将上述代码中的:

$(obj) : ${cpp}      
	@g++ -c $(cpp) -o $(obj)

替换成下面代码:

$(obj) : ${cpp}    
	@g++ -c $< -o $@

常用符号

1. =(常规赋值运算符)

特点: 变量可被反复赋值

a = 64
b = $(a)  #这里a为64,b为64

b = 75    #这里b为75

debug:
	@echo $(b)  #输出b时结果为75 

可自行用make debug命令尝试,这里就不贴结果图了。

2. :=(立即赋值运算符)

特点: 变量被赋值后不可更改,即便你重新定义。

a := 64
b := $(a)  #这里a为64,b为64

a := 75    #这里a为75

debug:
	@echo $(b)  #输出b时结果为64    b引用的a,即便a已经重新赋值

3. ?=(默认赋值运算符)

特点:
  如果该变量已经定义,则不进行任何操作
  如果该变量尚未定义,则求值并分配

a = 64
a ?= 75 #a之前已经被定义过,故:=不进行任何操作

debug:
	@echo $(a) #a输出仍然为64
a =    #什么都不写,此时默认赋值 空字符 
a ?= 75 #a之前已经被定义过,故:=不进行任何操作

debug:
	@echo $(a) #a输出为 空字符
a ?= 75 #a之前没被定义过,故:=等同于=

debug:
	@echo $(a) #a输出为75

4. +=(累加赋值运算符)

特点: 把多个字符串连接成一个字符串。

a := world!

b := hello
b += $(a)

debug:
	@echo $(b)  #输出为hello world!

5. \(续行符)

特点: 把多行变成一行。

a := Where does \
    AIs intelligence \
    come from? 

debug:
	@echo $(a) 
#输出完整的一句话:Where does AIs intelligence come from?
  • 0
    点赞
  • 0
    收藏
    觉得还不错? 一键收藏
  • 0
    评论
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值