当前位置: 首页 > news >正文

《Linux篇》自动化构建-make/Makefile

文章目录

  • 0.背景
  • 1.基本使用

在上一篇文章中,我们学习了使用gcc来编译我们的程序,但是那种方式貌似只能编译一个文件,当我们有很多源文件的时候怎么办呢?这时候就需要使用自动化构建make/Makefile了。

0.背景

  1. make是一个Linux系统内置的命令,makefile/Makefile是一个需要工程师自己构建的一个文件。两个搭配使⽤,完成项⽬⾃动化构建。
  2. ⼀个⼯程中的源⽂件不计数,其按类型、功能、模块分别放在若⼲个⽬录中,makefile定义了⼀系列的规则来指定,哪些⽂件需要先编译,哪些⽂件需要后编译,哪些⽂件需要重新编译,甚⾄于进⾏更复杂的功能操作。
  3. makefile带来的好处就是⸺“⾃动化编译”,⼀旦写好,只需要⼀个make命令,整个⼯程完全⾃动编译,极⼤的提⾼了软件开发的效率。
  4. make是⼀个命令⼯具,是⼀个解释makefile中指令的命令⼯具,⼀般来说,大多数的IDE都有这个命令,⽐如:Delphi的make,Visual C++的nmake,Linux下GNU的make。可见,makefile都成为了⼀种在⼯程⽅⾯的编译方法。

1.基本使用

code.c文件:
在这里插入图片描述
我们创建一个Makefile文件,里面的内容如下:
在这里插入图片描述
我们输入make指令就可以编译我们的程序了:
在这里插入图片描述
我们还可以在Makefile里面加入清理的功能:
在这里插入图片描述
输入make clean就可以清理掉了:
在这里插入图片描述
细节:
在这里插入图片描述
在这里插入图片描述
Q1:为什么make一下就默认的是上面的那个gcc,而make clean是下面的rm呢呢?
A1:make默认只形成一个目标,而扫描是从上往下扫描的,如何你上面的两个目标换个顺序,make就是rm和,make code才是gcc。

Q2:什么是伪目标呢?
A2:.PHONY:表示被修饰的目标是一个伪目标 -> 伪目标总是被执行的。什么叫不被执行 -> 如下图,make是不可以多次编译的,他已经是最新的了(Makefile让我们的编译工作尽可能高效一些)。如果我们给code也加上.PHONY,他就是总被执行的了。

最佳实践:可执行程序,不需要修饰为PHONY,clean修饰总是执行的。

Q3:make/makefile怎么知道我要不要重新编译呢?
A3:这就要将其我们之前学过的一个命令了:stat。.c文件和.exe都有modify时间,第一次编译完.exe的modify时间是肯定比.c文件的modify时间新的,如果.c文件一直没有修改,那也就不需要make了,而如果修改了.c文件的内容,那么他的modify时间就更新了,就可以再次make了。
在这里插入图片描述

在这里插入图片描述
一般文件内容(modify)发生改变,文件属性(change)也一定会发生改变。文件属性改变,文件内容不一定会发生改变,比如说我们chmod修改权限,只有change会修改。

Q4:为什么我们修改了文件内容,文件也被打开了,为什么access时间没有改变?
A4:现在Linux为了缓解压力,因为文件访问时间是非常频繁的,现在内核修改为访问文件多次,才会修改这个时间,这个参考意义不大。
在这里插入图片描述
在这里插入图片描述
在这里插入图片描述
其实对于上面完整的make,对应的应该是如下内容:
在这里插入图片描述
在这里插入图片描述
整个流程如下:
在这里插入图片描述
这个过程是make自动推导的,这个过程其实是利用栈数据结构进行推导的:
在这里插入图片描述
完整内容如下:
在这里插入图片描述
但是我们不会这么写,一般情况下,我们都是如下的这种写法,先生成目标文件,再链接·:
在这里插入图片描述
在这里插入图片描述
扩展Makefile,我们只需要修改对应的变量名即可,每个项目都用一套相同的Makefile文件:
在这里插入图片描述
在这里插入图片描述
优化点:
在这里插入图片描述
再进一步优化:
在这里插入图片描述

http://www.dtcms.com/a/277289.html

相关文章:

  • GraphRAG Docker化部署,接入本地Ollama完整技术指南:从零基础到生产部署的系统性知识体系
  • AI抠图软件,本地运行超快速
  • 水往低处流,人也往低处走
  • 三种网络类型
  • 跨域中间件通俗理解
  • 教程:如何查看浏览器扩展程序的源码
  • Linux驱动11 --- buildroot杂项驱动开发方法
  • 网络资源模板--基于Android Studio 实现的音乐播放器App
  • 【Go语言-Day 19】深入理解Go自定义类型:Type、Struct、嵌套与构造函数实战
  • 系规备考论文:论IT服务知识管理
  • 20250711_Sudo 靶机复盘
  • vue的优缺点
  • React强大且灵活hooks库——ahooks入门实践之状态管理类hook(state)详解
  • 在NDK开发中如何正确创建JNI方法
  • Perl小骆驼学习笔记 - 9. 用正则表达式处理文本
  • 香港服务器Python自动化巡检脚本开发与邮件告警集成
  • 《雨下小暑》诗赏——小暑时节暴雨之晨的清凉视听(智普清言)
  • iOS UI视图面试相关
  • 从儿童涂鸦到想象力视频:AI如何重塑“亲子创作”市场?
  • [特殊字符]使用 Nginx 将 HTTP 重定向到 HTTPS
  • Anaconda3安装教程(Windows)
  • 低代码引擎核心技术:OneCode常用动作事件速查手册及注解驱动开发详解
  • Web应用性能优化之数据库查询实战指南
  • 楼宇自动化:Modbus 在暖通空调(HVAC)中的节能控制(二)
  • 【Linux系统与网络编程】06:进程间通信
  • Day 19: 标准库巡礼:Python的“百宝箱”
  • c++学习之---红黑树的实现
  • CentOS 7 升级系统内核级库 glibc 2.40 完整教程
  • MSVCP*.dll、vcruntime*.dll缺失或损坏,以及.NET Framework相关问题,解决办法
  • 移动端设备本地部署大语言模型(LLM)