【Linux】Make/Makefile
这个3/4行的语法和1/2行是一样的。也是依赖关系和依赖方法。
make命令扫描makefile文件时,从上向下扫描,默认形成一个目标文件。
指定make clean
的时候才回去执行对应的清除。
为什么要给我们的clean.PHONY:clean
声明它是伪目标呢?
PHONY类似一种建议性的关键字。
伪目标,表示对应的依赖方法和依赖关系总是被执行。
什么叫不被执行?
我们上面的这组可执行程序没有被修饰,所以我们如果make完又make,是不会执行的。但如果用为目标修饰了,就会发现也可以执行。
所以我们一般可执行程序不用伪目标修饰,因为如果代码没有更新,没有必要再次编译。
默认老代码不作重新编译。
make怎么知道bin和.c的新旧?
Linux下每一个文件有三个相关时间,分别是Access/Modify/Change
文件=内容+属性
cat打印内容,ls打印属性
如果我们只改文件内容,那么Modify时间被修改。
如果我们只改文件属性,那么Change时间被修改。
如果不修改,单纯查看,Access时间被更新。
可以看到,这样我们的Modfiy时间就被改了。
而且文件属性页同步变化了,所以时间也改了:
大小和时间本就是文件的属性,所以基本都会同时修改。
更改这个权限,我们就是只改属性。
如果过于高频因为查看就更新时间,会有很多隐性的成本。所以linux现在查看上若干次才会更新一次Access时间,具体多少次看具体系统。
我们知道,myproc.c的Modify时间应当是要比myroc早的。所以make可以以此为依据判断myproc.c是否被修改过了。
我们曾经说过,touch可以用来改文件时间:
比如带上-a,就可以只改Access时间。
如果什么选项都不带,就会把ACM三个时间全部更新。
所以通过touch更改时间,也能使我们重复使用make。
所以PHONY的作用就是修饰后总是被执行,如果我们用其修饰第一组的代码,我们就可以重复使用make。
在makefile中注释代码我们使用#来注释。
makefile会在自己内部维护一个类似栈结构的东西。
makefile推导规则
从上往下扫描,从下往上执行。
当我们从上往下扫描,一条找不到时就入栈。所以就保证了我们最后找到myproc.c时,从下往上的执行顺序。
当然我们一般不会这么去写整个过程,自己增加难度。
makefile也允许我们去定义变量。所以我们写makefile一般喜欢这样写:
如果改写成这样:
就不会回显命令。
这样,BIN是我们的目标文件,CC是编译器,SRC是源文件,FLAGS是方法。我们将这组变量打印。
$(BIN)
就是取它的内容。
所以我们全以变量的形式呈现了。这就是一个基于变量版本的makefile了。
有点像宏。
所以我们也能猜出,这样做的好处也就是替换具体的文件时不用改后面的代码了,只要在变量处稍作修改。
其实,还可以写得更加优雅:
$@
代表的是目标文件,$^
代表的是依赖的众多文件列表。
我们的依赖方法来源不止一行。
我们可以把默认的显示信息用@关闭,然后写自己的信息:
但我们发现还是将echo
回显了,于是我们继续优化:
多文件呢?
而且,我们并不喜欢直接从.c到可执行文件,而是喜欢先从.c到.o,原因以前说过,为了方便去链接C语言库等,所以我们要改写。
LFLAGS的L代表link。OBJ代表.o文件。
.o文件从哪来的?所以我们要再写一组依赖关系和方法。但是一般我们的.c文件和以此生成的.o文件不止一个,为了简写,我们使用%.o:%.c
这样来写我们的依赖关系。%就像makefile模式下的通配符;在依赖关系中我们也简写为:$(CC) $(FLAGES) $<
,也是gcc -c $<
,这里<
用来简写所有的.c文件。
我们知道,gcc -c myproc.c -o myproc.o
可以帮我们从.c文件编译到.o文件。
然后,gcc -c myproc.c
则可以帮我们直接编译出同名.o文件。
这也就是为什么上面我们写成$(CC) $(FLAGS) $<
优化:
这个地方,我们可以SRC=$(shell ls *.c)
执行ls *.c
的命令,然后把对应所有的源文件放在SRC中。就不用我们一个一个手写要的源文件了。
第二种做法:
makefile天生自带类似函数的东西,可以支持我们这样写:SRC=$(wildcard *.c)
也是类似通配符。
所以我们的OBJ同样也需要这样能够使用类似通配符的效果,来避免一个一个手写。
OBJ=$(SRC:.c=.o)
这就是最终的makefile。
我们这样来创建100个文件:
不用改刚才的makefile文件了,可以直接这样使用make和make clean:
Makefile还有其他语法,日后可以再学。
相关文章:

【Linux】Make/Makefile
这个3/4行的语法和1/2行是一样的。也是依赖关系和依赖方法。 make命令扫描makefile文件时,从上向下扫描,默认形成一个目标文件。 指定make clean的时候才回去执行对应的清除。 为什么要给我们的clean.PHONY:clean声明它是伪目标呢? PHONY类…...

C++练级计划->《多态》虚函数表,菱形继承多态
目录 什么是多态? 多态的条件 虚函数: 虚函数的重写: 协变 析构函数的重写 C11 final 和 override final: override: 总结: 三重对比:重载重写重定义对比 抽象类 多态的原理 虚函数…...
OkHttp3 - 2. OkHttp的核心组件与架构
1 OkHttp的工作原理 OkHttp3 的核心设计遵循以下原则: 请求与响应的分离:通过 Request 和 Response 对象解耦请求构建与结果处理。异步与同步支持:使用 Call 对象管理请求,可以同步或异步执行。高效连接复用:通过连接…...
异或操作解决一些问题
前提: 异或操作符合交换律,结合律(因为其根本上来抽象理解,就是查看所有项二进制数相同位是否有奇数个1,对运算结果二进制数而言,没有该位为0,有该位为1,与顺序无关)。 …...

操作系统之输入输出
🧑 博主简介:CSDN博客专家,历代文学网(PC端可以访问:https://literature.sinhy.com/#/literature?__c1000,移动端可微信小程序搜索“历代文学”)总架构师,15年工作经验,…...
Centos 安装 Node.js 和 npm
方法2:使用 NVM(Node Version Manager)安装 安装 NVM curl -o- https://raw.githubusercontent.com/nvm-sh/nvm/v0.39.0/install.sh | bash 重新加载配置 source ~/.bashrc 安装最新的 LTS 版本的 Node.js nvm install --lts 验证安装…...

C语言——指针初阶(一)
目录 一.什么是指针??? 指针是什么? 指针变量: 总结: 总结: 二.指针和指针类型 指针-整数: 总结: 指针的解引用 总结: 三.野指针 如何规避野指针 往期…...
React Native 原生开发指南
写在前面 React Native (RN) 是一个用于构建跨平台移动应用的框架。它允许开发者使用 JavaScript 和 React 来编写应用程序,并将其转换为原生代码。虽然 RN 提供了许多内置的组件和 API,但有时候你可能需要访问原生平台的特定功能或性能优化。为此&…...

【前端】JavaScript中的柯里化(Currying)详解及实现
博客主页: [小ᶻ☡꙳ᵃⁱᵍᶜ꙳] 本文专栏: 前端 文章目录 💯前言💯什么是柯里化?💯柯里化的特点💯柯里化的简单示例💯通用的柯里化实现💯柯里化让代码更易读的原因💯…...
解决 docker 部署 vsftpd 速度慢问题
解决 docker 部署 vsftpd 速度慢问题 Docker 部署 ftp version: 3.8services:ftps:image: fauria/vsftpdcontainer_name: my-ftpsenvironment:- FTP_USERyourusername- FTP_PASSyourpassword- PASV_ADDRESS192.168.0.123 # 使用环境变量或直接指定IP地址- PASV_MIN_PORT4900…...
Java基础夯实——2.9 多线程如何共享数据
在 Java 多线程编程中,共享数据通过以下几种方式实现: 1. 使用共享对象 多个线程可以通过引用同一个对象来实现数据共享。例如: class SharedData {private int count;public synchronized void increment() {count;}public synchronized …...
【Leetcode Top 100】234. 回文链表
问题背景 给你一个单链表的头节点 h e a d head head,请你判断该链表是否为 回文链表(回文 序列是向前和向后读都相同的序列)。如果是,返回 t r u e true true;否则,返回 f a l s e false false。 数据…...

GitLab指定用户分配合并权限
进入项目 -》 Project Settings Repository -》展开 Protected branches -》 添加要保护的分支,设置角色 管理用户角色权限 查看到不同用户的角色,一般设置Developer只有Merger Request权限,Maintainer还有Merge审批权限 GitLab 中的权限…...

五,[GXYCTF2019]Ping Ping Ping1
进入靶场,有提示 我们在url试着输入本地IP,返回了ping命令 既然要在url处传参,那就用postman,再输入ip127.0.0.1 & ls,试着列出目录内容 ok,好像是个脏话,它过滤了空格 试着穿越又看到了脏话࿰…...
基于STM32的智能无人机自主飞行与目标识别系统设计
目录 引言系统需求分析 2.1 功能需求 2.2 硬件需求 2.3 软件需求系统设计 3.1 总体架构 3.2 各模块设计系统实现 4.1 硬件实现 4.2 软件实现系统调试与优化总结与展望 1. 引言 随着无人机技术的快速发展,无人机在军事侦察、环境监测、物流配送等领域的应用逐渐增多…...

C 语言数组与函数:核心要点深度剖析与高效编程秘籍
我的个人主页 我的专栏:C语言,希望能帮助到大家!!!点赞❤ 收藏❤ 目录 引言数组基础 2.1 数组的定义与初始化 2.2 一维数组的基本操作 2.3 二维数组及其应用 2.4 数组与指针的关系函数基础 3.1 函数的定义与调用 3.2…...

汽车轮毂结构分析有哪些?国产3D仿真分析实现静力学+模态分析
本文为CAD芯智库原创,未经允许请勿复制、转载! 之前分享了如何通过国产三维CAD软件如何实现「汽车/汽配行业产品设计」,兼容NX(UG)、Creo(Proe),轻松降低企业上下游图纸交互成本等。…...

解决jupyter notebook 新建或打开.ipynb 报500 : Internal Server Error(涉及jinja2兼容性问题)
报错: [E 10:09:52.362 NotebookApp] 500 GET /notebooks/Untitled16.ipynb?kernel_namepyt hon3 (::1) 93.000000ms refererhttp://localhost:8888/tree ...... 重点是: from .exporters import * File "C:\ProgramData\Anaconda3\lib\site-p…...

【若依ruoyi Vue前端线上个人服务器部署】以及常见报错问题解决
提示:【若依ruoyi Vue前端线上个人服务器部署】以及常见报错问题解决 文章目录 前言一、若依ruoyi Vue前端部署常见两种错误1、404问题2、找不到….模块 二、使用步骤(正式开始)1.修改vue.config.js中的publicPath属性。2.修改router/index.j…...

Python学习第十天--处理CSV文件和JSON数据
CSV:简化的电子表格,被保存为纯文本文件 JSON:是一种数据交换格式,易于人阅读和编写,同时也易于机器解析和生成,以JavaScript源代码的形式将信息保存在纯文本文件中 一、csv模块 CSV文件中的每行代表电…...
浏览器访问 AWS ECS 上部署的 Docker 容器(监听 80 端口)
✅ 一、ECS 服务配置 Dockerfile 确保监听 80 端口 EXPOSE 80 CMD ["nginx", "-g", "daemon off;"]或 EXPOSE 80 CMD ["python3", "-m", "http.server", "80"]任务定义(Task Definition&…...
Go 语言接口详解
Go 语言接口详解 核心概念 接口定义 在 Go 语言中,接口是一种抽象类型,它定义了一组方法的集合: // 定义接口 type Shape interface {Area() float64Perimeter() float64 } 接口实现 Go 接口的实现是隐式的: // 矩形结构体…...
Linux简单的操作
ls ls 查看当前目录 ll 查看详细内容 ls -a 查看所有的内容 ls --help 查看方法文档 pwd pwd 查看当前路径 cd cd 转路径 cd .. 转上一级路径 cd 名 转换路径 …...

苍穹外卖--缓存菜品
1.问题说明 用户端小程序展示的菜品数据都是通过查询数据库获得,如果用户端访问量比较大,数据库访问压力随之增大 2.实现思路 通过Redis来缓存菜品数据,减少数据库查询操作。 缓存逻辑分析: ①每个分类下的菜品保持一份缓存数据…...

C++ 求圆面积的程序(Program to find area of a circle)
给定半径r,求圆的面积。圆的面积应精确到小数点后5位。 例子: 输入:r 5 输出:78.53982 解释:由于面积 PI * r * r 3.14159265358979323846 * 5 * 5 78.53982,因为我们只保留小数点后 5 位数字。 输…...
C++八股 —— 单例模式
文章目录 1. 基本概念2. 设计要点3. 实现方式4. 详解懒汉模式 1. 基本概念 线程安全(Thread Safety) 线程安全是指在多线程环境下,某个函数、类或代码片段能够被多个线程同时调用时,仍能保证数据的一致性和逻辑的正确性…...
AspectJ 在 Android 中的完整使用指南
一、环境配置(Gradle 7.0 适配) 1. 项目级 build.gradle // 注意:沪江插件已停更,推荐官方兼容方案 buildscript {dependencies {classpath org.aspectj:aspectjtools:1.9.9.1 // AspectJ 工具} } 2. 模块级 build.gradle plu…...

Reasoning over Uncertain Text by Generative Large Language Models
https://ojs.aaai.org/index.php/AAAI/article/view/34674/36829https://ojs.aaai.org/index.php/AAAI/article/view/34674/36829 1. 概述 文本中的不确定性在许多语境中传达,从日常对话到特定领域的文档(例如医学文档)(Heritage 2013;Landmark、Gulbrandsen 和 Svenevei…...
高效线程安全的单例模式:Python 中的懒加载与自定义初始化参数
高效线程安全的单例模式:Python 中的懒加载与自定义初始化参数 在软件开发中,单例模式(Singleton Pattern)是一种常见的设计模式,确保一个类仅有一个实例,并提供一个全局访问点。在多线程环境下,实现单例模式时需要注意线程安全问题,以防止多个线程同时创建实例,导致…...

VM虚拟机网络配置(ubuntu24桥接模式):配置静态IP
编辑-虚拟网络编辑器-更改设置 选择桥接模式,然后找到相应的网卡(可以查看自己本机的网络连接) windows连接的网络点击查看属性 编辑虚拟机设置更改网络配置,选择刚才配置的桥接模式 静态ip设置: 我用的ubuntu24桌…...