Linux:make/makefile的使用
一、什么是makefile/make
会不会写makefile,从一个侧面说明了一个人是否具备完成大型工程的能力 一个工程中的源文件不计数,其按类型、功能、模块分别放在若干个目录中,makefile定义了一系列的 规则来指定,哪些文件需要先编译,哪些文件需要后编译,哪些文件需要重新编译,甚至于进行更复杂 的功能操作 makefile带来的好处就是——“自动化编译”,一旦写好,只需要一个make命令,整个工程完全自动编 译,极大的提高了软件开发的效率。 make是一个命令工具,是一个解释makefile中指令的命令工具,一般来说,大多数的IDE都有这个命 令,比如:Delphi的make,Visual C++的nmake,Linux下GNU的make。可见,makefile都成为了一 种在工程方面的编译方法。 make是一条命令,makefile是一个文件,两个搭配使用,完成项目自动化构建。

而make则是指令,makefile里保存的是依赖关系和依赖方法。
1.1makefile文件的编写

首先我们先touch一个makefile.c的文件,以往我们需要在命令行进行gcc去手动编译形成可执行程序,但通过makefile文件我们可以很好的释放自己的双手。

第一行表明依赖关系:要形成的文件为mybin,依赖文件为没有test.c。冒号的左边被称为目标文件,右边为依赖文件列表
第二行则是要执行的指令即依赖方法,使用gcc编译器形成mybin文件,源文件为mytest.c。
这样我们直接调用make指令就可以形成名为mymakefile的可执行程序。



然后运行mymakefile,就可以执行刚刚自己编写的makefile.c的程序了。

当我们再次make时,因为已经生成了可执行程序,而且我们对依赖文件并没有进行修改,所以这里就会make失败。此时如果我们对依赖文件做出修改就可以重新编译成功。
1.2makeclean
那我们如何清理项目呢?

我们可以通过设置自动化清理make clean来删除刚刚生成的可执行文件。

这时如果我们将 clean与mymakefile调换位置,再次去make就默认去调用clean。
所以make和Makefile形成目标文件的时候,默认时从上到下扫描makefile文件的,默认形成的时第一个目标文件。
那make和makefile怎么知道可执行程序即依赖文件是不是最新的呢?是通过对比时间对比出来的,只要可执行程序最近的修改时间比所有源文件的最近修改时间新,就说明它就是最新的。在逻辑上可执行和源文件的时间是不可能一样的。
1.3文件时间

stat查看文件详细信息可以看到时间。
文件=内容+属性,如果对内容更新,Modify的时间就会更新,如果对文件的属性做更新,Change的时间就会改变。

比如ll,就可以查看文件详细属性信息,如果我们用chmod对文件的权限进行修改,再次查看文件的详细信息就可以看到chang显示的时间被更改。而我们对内容即Modify更改时,change也会改变,因为更改内容会对文件大小造成改变,属性change也会跟着改变

Access是指上一次查看文件的时间,而查看文件的次数比更改文件内容属性的次数要多得多,如果每次查看都要更改Access, 那如果短时间内多次查看文件就会导致操作系统反复向磁盘更改文件的Access信息,导致系统本身变得低效。所以并不会每次都更新。
所以make指令在判断是否要重新生成目标文件时,比较的是依赖文件和已经生成的目标文件的Modify时间,当然我们也可以使用touch对依赖文件的Modify时间进行刷新,刷新后再使用make去重新覆盖生成目标文件。
而在非常大型的项目中,上百万行的代码,编译器在编译的时候可能会耗费十几二十分钟,如果我们对其中一个文件做修改,再次编译,编译器会根据时间判断修改了哪个,然后将其重新编译然后和其他没有修改的已经编译好的文件进行融合链接,大大提高了效率节省了时间。所以判断新旧时间是很有必要的。
二、make语法补充
2.1 .PHONY

.PHONY用来修饰目标文件,成为一个伪目标,总是被执行。这样每次调用相关指令都会无脑进行重新编译不会再去检查新旧文件的相关时间属性。
2.2$@ $^

当出现文件名比较长或者较为复杂时,我们可以使用 $@ $^来让编译器根据上面的依赖关系进行推导,$@表示目标文件 $^表示依赖文件。


也可以通过自定义变量然后进行替换,类似于宏的用法,依然可以实现make功能。
2.3make和makefile的语法推导

最终要形成的目标文件为mymakefile,我们可以根据程序的编译顺序,预处理编译汇编链接四个步骤来反向将文件从.c开始进行推导,形成最终的可执行程序需要.o文件,形成.o需要.s,形成,s需要.i,形成.i需要.c。所以从源文件到最终可执行是编译器这样一步步进行处理过来的,这就是make语法的推导过程。

最后就对依赖关系进行推导然后逆向执行依赖方法,最终形成目标文件mymakefile。
当然我们平日里不需要这样的写法来折磨自己。只需了解其原理就ok。
相关文章:
Linux:make/makefile的使用
一、什么是makefile/make 会不会写makefile,从一个侧面说明了一个人是否具备完成大型工程的能力 一个工程中的源文件不计数,其按类型、功能、模块分别放在若干个目录中,makefile定义了一系列的 规则来指定,哪些文件需要先编译&am…...
Java设计模式—策略模式(商场打折)
策略这个词应该怎么理解,打个比方说,我们出门的时候会选择不同的出行方式,比如骑自行车、坐公交、坐火车、坐飞机、坐火箭等等,这些出行方式,每一种都是一个策略。 再比如我们去逛商场,商场现在正在搞活动&…...
FOR循环
oracle从入门到总裁:https://blog.csdn.net/weixin_67859959/article/details/135209645 前面两种循环都要根据条件是否成立而确定循环体的执行,具体循环体执行多少次事先并不知道。 FOR 循环可以控制循环执行的次数,由循环变量控制循环体的…...
C++: 命名空间/C++输入输出/缺省参数/函数重载/引用/内联函数
进入C以后,就翻开了新的篇章。C支持C语言的使用。事实上,C是创建者在发现C语言中有很多不好用的地方(在后续学习中会明显看到)后,在C语言基础上又加入了许多语法,于是就成了C。 1.命名空间 来源ÿ…...
Java | Leetcode Java题解之第13题罗马数字转整数
题目: 题解: class Solution {Map<Character, Integer> symbolValues new HashMap<Character, Integer>() {{put(I, 1);put(V, 5);put(X, 10);put(L, 50);put(C, 100);put(D, 500);put(M, 1000);}};public int romanToInt(String s) {int …...
题目:学习使用register定义变量的方法。
题目:学习使用register定义变量的方法。 There is no nutrition in the blog content. After reading it, you will not only suffer from malnutrition, but also impotence. The blog content is all parallel goods. Those who are worried about being cheated …...
IO_DAY7
1:实现2个终端之间的互相聊天 要求:千万不要做出来2个终端之间的消息发送是读一写的,一定要能够做到,一个终端发送n条消息,另一个终端一条消息都不回复都是没有问题的 终端A: #include<myhead.h> int main(int argc, char…...
大模型学习笔记八:手撕AutoGPT
文章目录 一、功能需求二、演示用例三、核心模块流程图四、代码分析1)Agent类目录创建智能体对象2)开始主流程3)在prompt的main目录输入主prompt和最后prompt4)增加实际的工具集tools(也就是函数)5…...
Java常用API_System——常用方法及代码演示
1.System.exit(int status) 方法的形参int status为状态码,如果是0,说明虚拟机正常停止,如果非0,说明虚拟机非正常停止。需要将程序结束时可以调用这个方法 代码演示: public class Test {public static void main(S…...
neo4j图数据库下载安装配置
neo4j下载地址Index of /doc/neo4j/3.5.8/ 1.说明:jdk 1.8 版本对应的 neo4j 数据库版本 推荐安装3.X版本 2.配置系统环境变量 3.启动 neo4j.bat console 4.访问...
结构化面试-有矛盾的人际沟通题
例题一: 你和小张一起值班,但是小张没来,刚好领导检查发现后批评了他,事后小张埋怨你, 认为你在领导面前表现,并在同事中传播,同事也觉得你不通人情,你怎么处理? 回答&a…...
AI技术创业机会之金融科技
金融科技服务(FinTech)领域正经历着一场由人工智能(AI)技术引领的深刻变革,为创业者提供了无数创新与颠覆传统金融服务模式的机会。以下详述了金融科技服务中AI技术的具体创业机会及其细节与内容,以期为有志于涉足此领域的创业者提供全面的洞察与参考。 一、智能投顾与财…...
LC低通滤波
LC滤波器,是指将电感L与电容器 C进行组合设计构成的滤波电路,可去除或通过特定频率的无源器件。电容器具有隔直流通交流,且交流频率越高越容易通过的特性。而电感则具有隔交流通直流,且交流频率越高越不易通过的特性。因此&#x…...
CS162 Operating System笔记
What is an Operating System? it’s typically a special layer of software that provides the application access to hardware resources.So.it’s convenient abs fractions of complex hardware devices....
mysql慢sql排查与分析
当MySQL遇到慢查询(慢SQL)时,我们可以通过以下步骤进行排查和优化: 标题开启慢查询日志: 确保MySQL的慢查询日志已经开启。通过查看slow_query_log和slow_query_log_file变量来确认。 如果没有开启,可以…...
基于Springboot+Vue实现前后端分离酒店管理系统
一、🚀选题背景介绍 📚推荐理由: 近几年来,随着各行各业计算机智能化管理的转型,以及人们经济实力的提升,人们对于酒店住宿的需求不断的提升,用户的增多导致酒店管理信息的不断增多,…...
2024泰迪杯c题详细思路代码讲解:竞赛论文的辅助自动评阅
C:竞赛论文的辅助自动评阅 步骤一:理解拆解题目,并对附件1中的论文集进行初步分析。 步骤二:特征构造 论文完整性:开发算法以检查论文是否全面回答了赛题。这包括自然语言处理(NLP)技术来识别关键段落和论证的完整…...
【GEE实践应用】GEE下载遥感数据以及下载后在ArcGIS中的常见显示问题处理(以下载哨兵2号数据为例)
本期内容我们使用GEE进行遥感数据的下载,使用的相关代码如下所示,其中table是我们提前导入的下载遥感数据的研究区域的矢量边界数据。 var district table;var dsize district.size(); print(dsize);var district_geometry district.geometry();Map.…...
Excel 文件底部sheet 如何恢复
偶然打开一个excel文件,惊奇地发现:原来excel文件底部的若干个sheet居然全都看不到了。好神奇啊。 用其它的电脑打开同样的excel文件,发现:其实能看到的。说明这个excel文件并没有被损坏。只要将修改相关设置。就可以再次看…...
spring boot3登录开发-3(2短信验证登录/注册逻辑实现)
⛰️个人主页: 蒾酒 🔥系列专栏:《spring boot实战》 🌊山高路远,行路漫漫,终有归途 目录 写在前面 上文衔接 内容简介 功能分析 短信验证登录实现 1.创建交互对象 用户短信登录/注册DTO 创建用户登录VO…...
以下是对华为 HarmonyOS NETX 5属性动画(ArkTS)文档的结构化整理,通过层级标题、表格和代码块提升可读性:
一、属性动画概述NETX 作用:实现组件通用属性的渐变过渡效果,提升用户体验。支持属性:width、height、backgroundColor、opacity、scale、rotate、translate等。注意事项: 布局类属性(如宽高)变化时&#…...
《Playwright:微软的自动化测试工具详解》
Playwright 简介:声明内容来自网络,将内容拼接整理出来的文档 Playwright 是微软开发的自动化测试工具,支持 Chrome、Firefox、Safari 等主流浏览器,提供多语言 API(Python、JavaScript、Java、.NET)。它的特点包括&a…...
【配置 YOLOX 用于按目录分类的图片数据集】
现在的图标点选越来越多,如何一步解决,采用 YOLOX 目标检测模式则可以轻松解决 要在 YOLOX 中使用按目录分类的图片数据集(每个目录代表一个类别,目录下是该类别的所有图片),你需要进行以下配置步骤&#x…...
PL0语法,分析器实现!
简介 PL/0 是一种简单的编程语言,通常用于教学编译原理。它的语法结构清晰,功能包括常量定义、变量声明、过程(子程序)定义以及基本的控制结构(如条件语句和循环语句)。 PL/0 语法规范 PL/0 是一种教学用的小型编程语言,由 Niklaus Wirth 设计,用于展示编译原理的核…...
【python异步多线程】异步多线程爬虫代码示例
claude生成的python多线程、异步代码示例,模拟20个网页的爬取,每个网页假设要0.5-2秒完成。 代码 Python多线程爬虫教程 核心概念 多线程:允许程序同时执行多个任务,提高IO密集型任务(如网络请求)的效率…...
根据万维钢·精英日课6的内容,使用AI(2025)可以参考以下方法:
根据万维钢精英日课6的内容,使用AI(2025)可以参考以下方法: 四个洞见 模型已经比人聪明:以ChatGPT o3为代表的AI非常强大,能运用高级理论解释道理、引用最新学术论文,生成对顶尖科学家都有用的…...
蓝桥杯3498 01串的熵
问题描述 对于一个长度为 23333333的 01 串, 如果其信息熵为 11625907.5798, 且 0 出现次数比 1 少, 那么这个 01 串中 0 出现了多少次? #include<iostream> #include<cmath> using namespace std;int n 23333333;int main() {//枚举 0 出现的次数//因…...
大语言模型(LLM)中的KV缓存压缩与动态稀疏注意力机制设计
随着大语言模型(LLM)参数规模的增长,推理阶段的内存占用和计算复杂度成为核心挑战。传统注意力机制的计算复杂度随序列长度呈二次方增长,而KV缓存的内存消耗可能高达数十GB(例如Llama2-7B处理100K token时需50GB内存&a…...
LangChain知识库管理后端接口:数据库操作详解—— 构建本地知识库系统的基础《二》
这段 Python 代码是一个完整的 知识库数据库操作模块,用于对本地知识库系统中的知识库进行增删改查(CRUD)操作。它基于 SQLAlchemy ORM 框架 和一个自定义的装饰器 with_session 实现数据库会话管理。 📘 一、整体功能概述 该模块…...
uniapp 字符包含的相关方法
在uniapp中,如果你想检查一个字符串是否包含另一个子字符串,你可以使用JavaScript中的includes()方法或者indexOf()方法。这两种方法都可以达到目的,但它们在处理方式和返回值上有所不同。 使用includes()方法 includes()方法用于判断一个字…...
