Makefile 和 Bash 脚本之间区别和联系

目                    录

一、Makefile 和 Bash 脚本的定义    

(一)Bash 脚本

(二)Makefile

二、Makefile 和 Bash 脚本的相同之处

三、Makefile 和 Bash 脚本的不同点

(一)目的

(二)语法

(三)执行方式

(四)环境

(五)错误处理

(六)跨平台性

(七)应用场景不同

四、Makefile 和 Bash 脚本的语法

(一)相同点

(二)不同点

五、Makefile 和 Bash 脚本的应用

(一)Makefile应用场景

(二)Bash脚本应用场景


        我们在使用unix/linux的过程中,经常会碰到Makefile Bash 脚本,它们长得都比较像,很多命令还是相同的,那么,它们的命令是不是可以通用?有什么区别呢?

一、Makefile 和 Bash 脚本的定义    

(一)Bash 脚本

        Bash 脚本是一种使用 BashBourne Again SHellshell 编写的脚本文件。Bash 是一种流行的 Unix shell,它提供了丰富的命令行界面和强大的编程功能。Bash 脚本通常包含一系列命令,这些命令按照特定的顺序执行,以实现特定的任务或自动化过程。

(二)Makefile

        Makefile是为 Make 工具设计的,Make 工具用于控制编译和构建过程,特别是在大型项目中。Makefile 包含了一组规则和命令,这些规则和命令告诉 Make 如何从源代码生成目标文件(通常是可执行文件或库文件)。

二、Makefile 和 Bash 脚本的相同之处

1、自动化任务

        两者都可以用来自动化重复性或定期性的任务,从而减少手动操作的错误并提高效率。

2、脚本语言

        它们都是基于文本的脚本语言,可以通过编辑文本文件来创建和修改。

3、条件判断和循环

        Makefile和Bash脚本都支持条件判断和循环结构,使得脚本能够根据不同的条件执行不同的操作。

4、依赖管理

        两者都可以在某种程度上管理依赖关系。在Bash脚本中,可以通过命令的顺序来隐式地管理依赖。而在Makefile中,有一个更明确的依赖管理系统。

        另外,在 Makefile 中可以调用 Bash 脚本,或者在 Makefile 中直接写入 Bash 命令。这使得在构建过程中执行更复杂的任务成为可能。

三、Makefile 和 Bash 脚本的不同点

以下是 Makefile Bash 脚本之间的区别可以归纳为如下几个方面:

(一)目的

  1. Makefile:主要用于自动化编译和构建过程,尤其是当项目包含多个源文件,并且需要按特定顺序编译它们时。
  2. Bash 脚本:用于执行一系列命令以自动化任何类型的任务,不仅限于编译和构建。

(二)语法

  1. Makefile:具有其自己的语法,包括规则、目标、依赖项和命令。它通常比 Bash 脚本更简洁,因为它为常见的编译任务提供了很多内置规则。
  2. Bash 脚本:使用 Bash shell 的语法,包括变量、条件、循环等。

(三)执行方式

  1. Makefile使用 make 命令执行,可以指定一个目标(如果不指定,则通常执行第一个目标或默认目标)。可以很容易地并行执行多个命令,只需使用 -j 选项指定要同时运行的作业数。
  2. Bash 脚本:直接运行脚本,或者使用 bash 命令后跟脚本名。虽然也可以实现并行执行,但通常需要更多的脚本编写工作。

(四)环境

  1. Makefile:通常在开发环境中使用,特别是当需要编译源代码时。
  2. Bash 脚本:可以在任何支持 Bash 的环境中使用,不仅限于开发环境。

(五)错误处理

  1. Makefile:如果任何命令失败,Make 会停止执行,除非使用特定的错误处理规则。
  2. Bash 脚本:提供了更丰富的错误处理机制,包括条件、捕获和自定义错误消息。

(六)跨平台性

  1. Makefile虽然也主要用于Unix-like环境,但有一些变体(如NMake)可以在Windows上使用。
  2. Bash脚本:在大多数Unix-like系统上运行良好,但在Windows上可能需要额外的工具(如Cygwin或WSL)。

(七)应用场景不同

       这个不同在后面章节详细阐述。

四、Makefile 和 Bash 脚本的语法

MakefileBash脚本在语法上既有相似之处,又有明显不同。下面我将分别描述比较:

(一)相同点

  1. 变量赋值:Makefile和Bash脚本都支持变量赋值,并且可以使用这些变量来定制脚本的行为。在Bash中,变量赋值时等号两边不能有空格,例如VAR="value",而在Makefile中,等号两边可以有空格,例如VAR = value。不过,在Makefile中也可以使用:=来进行立即赋值,此时等号两边不能有空格。
  2. 条件判断:两者都支持条件判断,根据条件执行不同的代码块。在Bash中,这通常通过if、elif、else和fi关键字实现。在Makefile中,条件判断可以通过ifeq、ifneq、ifdef、ifndef等指令实现。
  3. 循环结构:Bash脚本和Makefile都支持循环结构,用于重复执行一段代码。在Bash中,常见的循环有for、while和until。在Makefile中,可以通过foreach来实现类似的循环功能。
  4. 函数/定义:Bash脚本支持函数定义,可以在脚本中调用这些函数。Makefile中没有函数的概念,但可以通过定义规则来达到类似的效果,规则中的命令可以被多次调用。
  5. 注释:两者都支持注释,可以在脚本中添加说明性文字。在Bash中,使用#开头表示注释。在Makefile中,同样使用#开头表示注释。

(二)不同点

  1. 基本结构:Bash脚本是基于命令行的,由一系列命令组成,按照顺序执行。而Makefile是基于规则的,由目标(target)、依赖(dependencies)和命令(commands)组成,通过指定目标来触发相应的规则执行。
  2. 命令执行:在Bash脚本中,命令直接执行,并且每条命令默认在当前shell中执行(除非使用子shell)。而在Makefile中,规则的命令通常在一个新的shell实例中执行,每条命令默认单独执行(可以通过.ONESHELL特殊目标改变这一行为)。
  3. 通配符:在Bash中,*用作通配符,匹配任意字符串。而在Makefile中,%用作通配符,用于模式匹配和自动变量。
  4. 命令连接:在Bash中,命令可以通过;、&&或||连接,分别表示顺序执行、条件执行(仅当前一个命令成功时)和条件执行(仅当前一个命令失败时)。而在Makefile中,命令通常通过换行符分隔,并且每条命令在一个独立的shell中执行(除非特别指定)。
  5. 错误处理:Bash脚本中,需要显式检查命令的退出状态来处理错误。而在Makefile中,如果任何命令执行失败(返回非零退出状态),则整个规则的执行将立即终止,并且Make会报告错误。
  6. 特殊字符处理:在Bash脚本中,特殊字符(如变量、引号、反斜杠等)的处理需要特别小心,以避免语法错误或意外的行为。而在Makefile中,由于它的语法和解析规则与Bash不同,特殊字符的处理也有所不同,例如$用于引用变量,@用于禁止命令回显等。
  7. 包含文件:在Makefile中,可以使用include指令来包含其他Makefile文件,从而实现模块化和复用。而在Bash脚本中,通常通过source或.命令来包含其他脚本文件。

        Makefile和Bash脚本由于它们的设计目标和用途不同,它们在基本结构、命令执行、通配符使用、错误处理等方面存在显著的差异。了解这些差异对于正确编写和理解MakefileBash脚本至关重要。

五、Makefile 和 Bash 脚本的应用

        Makefile和Bash脚本各自在不同的情境下被广泛应用。以下是它们主要的应用场景:

(一)Makefile应用场景

  1. 软件构建:Makefile是软件构建中最常见的工具之一,尤其在C、C++等需要编译的项目中。它定义了如何从源代码编译出可执行文件或库,并处理了文件间的依赖关系。
  2. 自动化构建:Makefile通过定义一系列的规则,可以自动化完成诸如编译、链接、测试、打包、安装等任务,提高开发效率。
  3. 版本控制:Makefile通常与版本控制系统(如Git)结合使用,以自动化处理构建相关的任务,如生成构建日志、清理构建产生的临时文件等。
  4. 项目文档生成:Makefile也可以用来自动化生成项目文档,如API文档、用户手册等。
  5. 清理和安装:Makefile通常包含清理(clean)和安装(install)目标,用于清理构建产生的临时文件和将最终产品安装到系统中。

(二)Bash脚本应用场景

  1. 系统管理和维护:Bash脚本经常用于系统管理员的日常任务,如监控磁盘空间、管理用户账户、备份数据、配置网络服务等。
  2. 自动化任务:Bash脚本可以自动化执行一系列命令行任务,如批量处理文件、下载和安装软件、定时执行某项任务等。
  3. 数据处理:Bash脚本经常用于处理文本和文件数据,如日志分析、文本搜索和替换、数据提取和转换等。
  4. 部署和配置:Bash脚本可以用于自动化部署应用程序或配置系统环境,如配置Web服务器、数据库服务器等。
  5. 与其他工具集成:Bash脚本可以与其他命令行工具和脚本语言(如Python、Perl等)集成,以创建更复杂的自动化解决方案。

        总之,Makefile主要用于编译和构建软件项目,而Bash脚本则更广泛地应用于系统管理和自动化任务。在实际工作中,两者可以结合使用,以创建一个完整、自动化的构建和部署流程。

本文来自互联网用户投稿,该文观点仅代表作者本人,不代表本站立场。本站仅提供信息存储空间服务,不拥有所有权,不承担相关法律责任。如若转载,请注明出处:http://www.mzph.cn/news/671810.shtml

如若内容造成侵权/违法违规/事实不符,请联系多彩编程网进行投诉反馈email:809451989@qq.com,一经查实,立即删除!

相关文章

Linux spell命令教程:如何进行拼写检查(附实例详解和注意事项)

Linux spell命令介绍 spell是一个拼写检查程序,它扫描文本文件中的拼写错误,并将每个拼写错误的单词单独打印出来。它基于原始的UNIX拼写检查器,非常简洁。如果一个单词不在spell的字典中,该单词就会被打印出来。 Linux spell命…

一个Vivado仿真问题的debug

我最近在看Synopsys的MPHY仿真代码,想以此为参考写个能实现PWM-G1功能的MPHY,并应用于ProFPGA原型验证平台。我从中抽取了一部分代码,用Vivado自带的仿真器进行仿真,然后就遇到了一个莫名其妙的问题,谨以此文作为debug…

ROS2 CMakeLists.txt 和 package.xml

这里记录一下ROS2中功能包package.xml和CMakeLists.txt的格式。以LIO-SAM的ROS2版本为例: 一:CMakeLists.txt cmake_minimum_required(VERSION 3.5) project(lio_sam)if(NOT CMAKE_BUILD_TYPE AND NOT CMAKE_CONFIGURATION_TYPES)set(CMAKE_BUILD_TYPE…

C语言之自定义类型:联合和枚举

目录 1. 联合体类型的声明2. 联合体的特点3. 联合体大小的计算联合的一个练习 4. 枚举类型的声明5. 枚举类型的优点6. 枚举类型的使用 1. 联合体类型的声明 像结构体一样,联合体也是由一个或者多个成员构成,这些成员可以不同的类型 但是编译器只为最大…

vCenterServer部署

一、硬件配置 vCenterServer本身最低的硬件要求是14GB,而vCenterServer则是以虚拟机的形式安装在ESXi中的虚拟机,所以ESXi的最低硬件要求是15.5GB,就是15872MB 二、安装vCenterServer 直接解压VMware-VCSA-all-8.0.0-20920323.iso&#xf…

TDengine用户权限管理

Background 官方文档关于用户管理没有很详细的介绍,只有零碎的几条,这里记录下方便后面使用。官方文档:https://docs.taosdata.com/taos-sql/show/#show-users 1、查看用户 show users;super 1,表示超级用户权限 0,表…

python实现飞书群机器人消息通知

python实现飞书群机器人消息通知(消息卡片) 直接上代码 """ 飞书群机器人发送通知 """ import time import urllib3 import datetimeurllib3.disable_warnings()class FlybookRobotAlert():def __init__(self):self.web…

【0258】pg内核支持的所有 inval messages 类型

1. inval messages类型 pg内核中,共支持几种类型的共享无效消息: (1)使特定catcache中的特定元组无效(2)使给定系统目录中的所有catcache项无效(3)使特定逻辑关系表的relcache条目…

一道sql注入的ctf题目致使用phpmyadmin上传 webshell 拿后台权限

以下均为靶场测试环境渗透&#xff0c;非正式环境。 遇见登录框&#xff0c;直接万能密码’or(11)or’/1 直接登录成功并返回结果: 既然存在sql注入&#xff0c;那就用sqlmap跑一下吧&#xff1a; 输出所有的数据库&#xff1a; sqlmap -u <目标URL> --dbs 要输出数据库…

代码随想录算法训练营第四十二天 | 416. 分割等和子集

题目链接&#xff1a;416. 分割等和子集 文章讲解&#xff1a;代码随想录 416. 分割等和子集讲解 视频讲解&#xff1a;动态规划之背包问题&#xff0c;这个包能装满吗&#xff1f;| LeetCode&#xff1a;416.分割等和子集 思路和解法 题目&#xff1a; 给你一个 只包含正整…

Android Button background 失效

问题 Android Button background 失效 详细问题 笔者开发Android项目&#xff0c;期望按照 android:background中所要求的颜色展示。 实际显示按照Android 默认颜色展示 解决方案 将xml的Button 组件修改为<android.widget.Button> 即将代码 <Buttonandroid:l…

「云原生可观测团队」获选「InfoQ 年度技术内容贡献奖」

随着云原生、人工智能逐渐成为各行各业的创新生产力工具。可以预见&#xff0c;我们即将进入全新的智能化时代。随着数据成为新型生产要素&#xff0c;云和 AI 正走向深度融合。云原生通过提供大规模多元算力的高效供给&#xff0c;可观测成为业务创新的核心基础设施&#xff0…

CSS伸缩盒模型

CSS伸缩盒模型 伸缩盒模型是CSS中的一种布局手段&#xff0c;可以使元素具有弹性&#xff0c;让元素可以跟随页面大小的改变而改变。 1. 伸缩容器 给元素设置display:flex 或 display:inline-flex &#xff0c;就是伸缩容器。 2. 主轴与侧轴 主轴&#xff1a; 伸缩项目沿着…

python coding with ChatGPT 打卡第17天| 二叉树:找树左下角的值、路径总和

相关推荐 python coding with ChatGPT 打卡第12天| 二叉树&#xff1a;理论基础 python coding with ChatGPT 打卡第13天| 二叉树的深度优先遍历 python coding with ChatGPT 打卡第14天| 二叉树的广度优先遍历 python coding with ChatGPT 打卡第15天| 二叉树&#xff1a;翻转…

SpringBoot+随机盐值+双重MD5实现加密登录

&#x1f3e1;浩泽学编程&#xff1a;个人主页 &#x1f525; 推荐专栏&#xff1a;《深入浅出SpringBoot》《java对AI的调用开发》 《RabbitMQ》《Spring》《SpringMVC》 &#x1f6f8;学无止境&#xff0c;不骄不躁&#xff0c;知行合一 文章目录 前言一、salt…

阿里云游戏服务器收费价格表,一年和1个月报价

阿里云游戏服务器租用价格表&#xff1a;4核16G服务器26元1个月、146元半年&#xff0c;游戏专业服务器8核32G配置90元一个月、271元3个月&#xff0c;阿里云服务器网aliyunfuwuqi.com分享阿里云游戏专用服务器详细配置和精准报价&#xff1a; 阿里云游戏服务器租用价格表 阿…

Linux系统调试课:硬件断点

沉淀、分享、成长,让自己和他人都能有所收获!😄 📢在linux内核编程中,经常会遇到由于内存被篡改,例如 buffer overflow,野指针,write after free等。查找分析此类问题非常的麻烦。 一、什么是硬件断点 硬件断点,是Linux内核中是一种被ptrace和内核内调试器使用调试…

Codeforces Round 923 (Div. 3) A - E

CF1927A Make it White 代码如下&#xff1a; //朴素版 #include<bits/stdc.h> using namespace std; using ll long long; const ll N 200005; #define inf 0x7fffffff void solve() {ll n;cin>>n;string a;cin>>a;ll x-1,y0;a a;for(ll i1;i<n;i){i…

【数据分享】1929-2023年全球站点的逐月平均降水量(Shp\Excel\免费获取)

气象数据是在各项研究中都经常使用的数据&#xff0c;气象指标包括气温、风速、降水、湿度等指标&#xff0c;说到常用的降水数据&#xff0c;最详细的降水数据是具体到气象监测站点的降水数据&#xff01; 有关气象指标的监测站点数据&#xff0c;之前我们分享过1929-2023年全…

为什么要用建造者模式

因为如果不使用建造者模式&#xff0c;使用一个类时&#xff0c;类中可能会创建很多重载的构造方法。 当使用了建造者模式&#xff0c;使用一个类时&#xff0c;可以选择性地给对象的属性赋值&#xff0c;避免类中可能会创建很多重载的构造方法。 以下是最简单的例子&#xff…