【Linux】Linux环境下如何实现自动化编译——make/makefile入门

文章目录

前言

一、make/Makefile 的使用

1.示例

2.编写 Makefile 文件

2.1生成

2.2清理

二、make 如何知道生成的可执行文件是否最新


前言

        在Linux 环境下编写好C语言代码之后,我们需要使用编译工具gcc 将其翻译为可执行文件。可是,如果对代码进行多次修改,每次修改完成,都需要重新使用 gcc 指令,会显得非常麻烦,所以可以使用 Linux 下的自动化构建工具 make/Makefile 。make是一条命令,Makefile是一个文件,两个搭配使用,完成项目自动化构建。
        此外,如果是写工程文件,那么一个工程中的源文件不计数,其按类型、功能、模块分别放在若干个目录中,Makefile 定义了一系列的规则来指定,哪些文件需要先编译,哪些文件需要后编译,哪些文件需要重新编译,甚至于进行更复杂的功能操作。。

        与此同时,平时使用如 Visual Studio 2019 等 IDE,是可以对程序进行调试的。在Linux环境下,也有专门的调试器 —— gdb。可以实现类似于 VS 环境下的调试,单步执行,监视变量、进入函数等等。


一、make/Makefile 的使用

1.示例

        上面说过,make是一条命令,Makefile是一个文件。显然,就类似于 vim 的配置文件一样,Makefile里面定义了某些规则,当我们使用make指令的时候,就可以有选择性地调用这些规则,比如编译文件、删除文件等等。

        下面通过一个例子来更好地理解这个内容。如下,编写了一个打印 "Hello World" 的测试文件,和简单的Makefile。

        根据 Makefile 里面的内容可以大致猜到,起作用就是 编译test.c 文件,生成 test 这个可执行文件。
        我们来测试一下,如下,直接使用 make 指令。发现自动执行上文写好的依赖方法,然后查看,确实生成了 test 文件,执行正常。

2.编写 Makefile 文件

2.1生成

        如上,Makefile 里面第一行的内容,可以理解为:我要生成一个目标文件 test,其依赖于 test.c 。我们把这种关系称为依赖关系第二行的内容被称作是依赖方法,其定义了:如何通过 test.c 生成 test 。我们可以再小小总结一下:Makefile 是围绕依赖关系和依赖方法进行自动化编译的工具。

        那么,我们可不可以分步来生成 test 文件呢?自然是可以的,由于冒号左边是依赖于冒号右边,所以我们可以如下图这样写,test 依赖于 test.o , test.o 依赖于 test.s ,test.s 依赖于 test.i ; test.i 依赖于 test.c 。 

        实际上,只使用 make 指令的话,只会执行 Makefile 里面的第一个依赖关系和依赖方法。但是,上图中,第一个依赖关系是 test : test.o , 可是当前目录下并没有 test.o 文件,下面又有 test.o 依赖于 test.s ,所以还要寻找 test.s …… 一直这样下去,直到找到最后一个依赖关系——  test.i 依赖于 test.c ,test.c 是存在的,所以可以执行这个依赖方法,那么生成了test.i ,又可以执行上面的依赖方法……(依次执行上面的依赖方法。)

       上面一步步生成 test 文件只是做一个示例,为了初步了解 Makefile ,一般情况下,不推荐这样,还是推荐最开始那样,直接生成。

2.2清理

        有时,我们会需要删除文件,也可以使用 Makefile 配置实现自动化删除。如下图,配置Makefile 里面多了一个关于 clean的 依赖关系 和 依赖方法。其中,可以看到,clean:的右边是没有内容的,即 clean 不依赖于任何文件,这种写法是可以的。但是 clean:不可以去掉,否则不知道这个依赖方法是属于哪个依赖关系。至于多出来的 .PHONY:clean 是什么意思,下文会讲解。

        但是,在命令行里执行的时候,为什么不是使用 make 而是 make clean 呢?其实上文提到过一些,如果只使用 make 指令,那么就会执行第一组依赖关系和依赖方法。但是,这里clean是第二组依赖关系和依赖方法,所以要使用 make clean ,让它知道我们要使用的是 clean 这一组依赖关系和依赖方法。

        可是 Makefile 文件里面为什么会多了一行 .PHONY:clean 呢?.PHONY: 是一个关键字,在这里被用来修饰 clean。.PHONY: 的意思是说:clean 总是被执行的。直接根据字面意思来理解可能会十分困难,可以通过例子来理解。下图中,使用 make 指令,第二次的时候却被告知 test 文件已经是最新的了,所以无法构建。但是,有 .PHONY: 修饰的 clean ,却可以一直执行

        所以可以以此来总结:有 .PHONY: 修饰之后,该组依赖关系和依赖方法不会因为文件的性质(是否存在、是不是最新版的)而决定执不执行,只要命令行输入了,那么就一定会被执行。注意,.PHONY: 修饰的,一般被称作伪目标

        我们用 .PHONY: 修饰 test 之后,就可以一直执行了,但是正常不会这样写,因为如果代码很多,那么编译代码是非常耗时间的。


二、make 如何知道生成的可执行文件是否最新

        上文有提到,如果不适用 .PHONY: 修饰 test,那么第二次执行 make 指令的时候,会提示 test 文件已经是最新的了,make 是如何判别的呢?

        实际上,由于 test 依赖于 test.c ,所以是根据 test.c 最后修改时间 ,和 test 的生成时间来判断。如果 test.c 最后修改时间 比 test 生成的时间早,那么这个 test 就是最新的;反之就不是最新的,可以重新生成。

        如下,一开始 test.c 文件最后修改时间是比 test 生成时间早;然后对 test.c 进行修改,明显看到其最后的修改时间变了比 test 文件的生成时间要晚,此时就可以执行 make  。成功编译,运行。

        根据这个特性,我们可以对 make 进行”欺骗“,即 test.c 文件里的内容不修改,但是也可以多次make。这就需要使用 touch 指令的特性 —— 执行 touch test.c ,如果 test.c 文件已经存在,就只会改变它的 最后修改时间 。根据这里就可以达到 "欺骗" ,如下图。

        关于 make / makefile 的知识就先讲到这里啦,有问题欢迎指出讨论!!

  • 3
    点赞
  • 29
    收藏
    觉得还不错? 一键收藏
  • 打赏
    打赏
  • 28
    评论

“相关推荐”对你有帮助么?

  • 非常没帮助
  • 没帮助
  • 一般
  • 有帮助
  • 非常有帮助
提交
评论 28
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包

打赏作者

努力努力再努力.xx

你的鼓励将是我创作的最大动力

¥1 ¥2 ¥4 ¥6 ¥10 ¥20
扫码支付:¥1
获取中
扫码支付

您的余额不足,请更换扫码支付或充值

打赏作者

实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

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

余额充值