shell (三)shell脚本

news2024/11/17 7:38:12
  • SHELL脚本

    • 编程语言的分类
      • 解释型语言:shell,Python,需要解析器

      • 编译型语言:C语言,C++,需要编译器

    • shell脚本

      • 操作系统的结构

        • shell(贝壳)

          • 应用层

            • app,代码

              • 应用层需要通过shell完成和内核的交互

          • 内核层

            • 设备管理

            • 文件管理

            • 网络管理

            • 进程管理

            • 内存管理

          • 硬件层

            • 外部设备

      • 第一个shell脚本

        • shell脚本的本质: 指令的集合

        • C语言文件 .c

          • shell文件 .sh

            • C++文件 .cpp

        • #!/bin/bash

          • #!用于指明该脚本默认使用shell解析器

          • 说明使用的是shell解析器

        • echo hello

          • 输出hello

            • echo 打印指令将hello输出

        • #

          • 在shell中表示注释

      • 执行脚本的三种方式

        • bash 文件名

          • 通过解析器,直接解析脚本

          • bash 1.sh

            • 执行过程:在后台打开一个终端

        • 直接运行脚本

          • 需要给脚本添加可执行权限

            • chmod 777 1.sh

            • 直接在终端输入1.sh

        • source 脚本名

          • 前台打开一个终端,执行脚本和返回脚本都在当前终端

    • 修改环境变量

      • 查看已有的特殊系统变量

        • env

      • 查看环境变量

        • echo $PATH

        • 环境变量的作用:当在终端直接运行指令时,去默认环境变量保存的路径中查找指令,如果没找到该指令不能执行

      • 修改环境变量

        • 只对当前终端有效

          • export PATH = ${PATH}:/home/ubunutu

            • export : 给系统变量赋值

            • PATH:被赋值的变量

            • =:赋值

            • ${PATH} : 拿到之前PATH的值

            • ::分隔

            • /home/ubuntu:添加的路径

          • 代码运行的作用:在当前终端给PATH添加了一个/home/ubuntu路径

        • 只对当前用户有效

          • 修改家目录下的~/.bashrc文件

            • 由于是当前用户下的家目录,所以不需要加sudo

          • vim ~/.bashrc

            • 然后将export表达式添加到文件的尾部

          • 修改文件后需要运行文件才能生效

            • source ~/.bashrc

            • 重启虚拟机

        • 对所有用户生效

          • 修改/etc/enviroment

            • sudo vim /etc/enviroment

              • 只有一行PATH的信息,想要添加的路径

          • 修改/etc/bash.bashrc文件

            • sudo vim /etc/bash.bashrc

              • 使用export表达式,添加路径

    • shell中的变量

      • shell中的变量没有数据类型的区别,shell是一种弱数据类型语言,都当字符串处理

      • 格式:

        • 变量名 = ‘变量的值’

          • 用于变量值内有空格时,无$获取变量的值

        • 变量名 = “变量的值”

          • 可以$变量的展开

        • 变量名 = 变量的值

          • = 号两侧不能有空格

      • 获取变量

        • $变量名

        • ${变量名}

          • 为了更好的区分变量名的范围

      • 修饰变量的关键字

        • readonly

          • 只读变量,值不能更改

        • unset

          • 清空变量的值,不能清空readonly修饰的值

        • local

          • 定义局部变量(只能在函数中使用)

      • 外部传参/位置变量

        • 和C语言相同,脚本也可以在执行时进行外部传参,shell中通过位置变量获取参数

        • $0

          • 获取脚本名

        • $n

          • 获取第n个外部参数

            • n>10时需在n外加上大括号,否则只能读取一位

        • $#

          • 获取所有外部参数的个数

        • $*/$@

          • 获取所有的外部参数

      • 输出

        • echo

          • echo 输出内容(将内容回显到终端,并自动换行)

          • echo默认不解析转义字符

          • echo -n 输出内容

            • 取消echo输出时的换行

          • echo -e "hello\n"

            • 解析转义字符

      • 指令的格式:指令 参数 操作数

        • 有些指令也支持:指令 操作数 参数

          • echo 不支持

        • 指令的标准格式

      • 输入

        • 复习:C中使用scanf、gets、getchar需要变量的地址

        • shell中使用read指令完成输出

        • read

          • read 变量名

            • 直接加变量名即可,可以读入带空格的数据

          • read -p "提示信息" 变量名

            • 在终端给用户输出提示信息

          • read -s 变量名

            • 输入的信息不回显

          • read -t 秒数 变量名

            • 如果n秒用户不输入,就结束输入向后执行语句

          • read -n 个数 变量名

            • 如果输入n个字符,自动停止

      • 命令置换符

        • 作用:获取指令的执行结果

        • `命令` (反引号)

        • $(命令)

    • shell中的数组

      • shell中支持稀疏数组

      • 定义

        • 数组名=(初始值1 初始值2 初始值3 ····)

        • #shell中的数组,不需要写出数组长度

        • #shell中数组初始化时,直接使用()

        • #shell中的数组每个元素之间是空格不是逗号

        • #访问仍然通过下标访问,并且下标仍然从0开始

        • 数组名=([下标]=初始值 [下标]=初始值 ····)

          • 下标可以不连续

      • 访问数组中的元素

        • ${数组名[下标]}

          • 获取数组中指定下标的元素的值

        • 要在shell中需要使用变量的值,都要用$进行访问

      • 获取数组中元素的个数

        • ${#数组名[*/@]}

          • 获取数组中已经赋值的元素的个数

        • ${#数组名[下标]}

          • 获取数组中指定下标元素的长度(字符个数)

      • 稀疏数组

        • 下标不连续的数组

        • 稀疏数组中元素的个数,由不为空的数据的个数决定

        • 数组名=([下标]=初始值 [下标]=初始值 ····)

          • 下标可以不连续 初始值可以是任意字符/串

      • 使用已有的数组给新的数组赋值

        • arr=(1 2 3 4 5) arr1=(a b c d) #定义一个arr2数组使用已有的arr和arr1数组赋值 arr2=(${arr1[*]} ${arr[*]}) #拼接加空格 echo ${arr2[*]} echo ${#arr2[*]}

          • 拼接时两个数组中间没有加空格, 第一个数组中的对后一个元素和第二个数组中的第一个元素会被拼接到一起

          • 拼接时两个数组中间加空格,两个数组独立起来拼接

    • shell中的运算

      • shell本身不擅长运算,需要借助运算符和其他指令

      • (())

        • 常用于shell中的整数算术运算

        • (())几乎支持所有的C语言语法

        • ((表达式1,表达式2,表达式3,·······)) 每一个表达式都会执行,获取最右侧一个表达式的结果

        • 想要获取运算的结果,需要使用$(()),还可以((变量名=表达式))

        • 在(())中,使用变量的值,可以加$也可以不加$ (建议在(())直接使用变量的值,不加$)

        • 在(())中,运算符两侧可以有空格

      • $[]

        • 变量名=$[表达式1,表达式2,表达式3,·······]只获取最右侧表达式的结果

        • 使用变量时,可以加$也可以不加$

        • 运算符两侧可以加空格,也可以不加空格

        • $[]的结果,建议直接按照"变量名=$[]"格式接收,因为$[]本质上,会遗留一个运算结果在表达式的位置,如果不接受继续向后运行指令会报错

      • let

        • let 变量名=表达式

          • let和变量名中间一定要有空格

        • let中使用变量,可以加$也可以不加$

        • let运算时,运算符两侧一定不能有空格

        • 如果直接写成 let 表达式,表达式会运行,但是没有返回值

      • expr

        • 格式:expr 表达式

        • 是一个终端指令

          • 故而expr中使用变量,必须加$

        • 如果想要接收expr的结果,必须使用命令置换符

        • expr中运算符两侧必须有空格,不支持自增、自减和shell中的幂运算

        • expr中使用某些运算符时,需要转义|、>、<、.、······ (不需要记转义字符,简单的指令在运行前,去终端里运行一下指令,没结果就加上转义字符)

        • expr指令的结果,可以直接回显到终端上,故使用命令置换符接收回显值

        • expr操作数的值不能为空

          • 如果expr的操作数为空会报语法错误

        • expr进行整数算术运算

        • expr(字符串运算)

          • match 字符串 表达式

            • 返回表达式,在字符串中第一个位置起完全匹配成功的字符个数,如果能够匹配成功,返回值就是表达式中字符的个数

            • expr match "$str1" $str2

              • 由于str1中有空格,需用双引号引起来

            • str2不能在str1中的第一个位置开始完全匹配返回0

          • substr 字符串 偏移量 长度

            • 从字符串中偏移量的位置开始 截取指定长度的字串,偏移量从1开始

            • expr substr "$str1" 7 5

              • 截取出字符串的子串world

              • substr : 字符串的子串

          • index 字符串 字符

            • 返回字符在字符串中第一次被查找到时的下标,下标从1开始

            • expr index "$str1" el

              • 返回下标2

              • index:指标

            • 如果查找多个字符在字符串中的位置 返回最先出现的字符的位置

          • length 字符串

            • 返回字符串的长度

            • expr length "$str1"

    • if 分支结构

      • shell中的if语句格式

        • 单分支结构

          • if [ test语句 ] then 语句块 fi

        • 双分支结构

          • if [ test语句 ] then 语句块 else 不满足条件执行的语句 fi

        • 多分支结构

          • if [ test语句1 ] then 满足语句1执行的语句块 elif [ test语句2 ] ------> elif test 表达式 then 不满足语句1满足语句2执行的语句 else 两个都不满足语句块 fi

      • if对整数进行判断

        • ARG1 -eq ARG2: ARG1和ARG2相等

          • -eq : INTEGER1 is equal to INTEGER2

        • ARG1 -ge ARG2: ARG1>=ARG2

          • -ge : INTEGER1 is greater than or equal to INTEGER2

        • ARG1 -gt ARG2: ARG1>ARG2

          • -gt : INTEGER1 is greater than INTEGER2

        • ARG1 -le ARG2: ARG1<=ARG2

          • -le : INTEGER1 is less than or equal to INTEGER2

        • ARG1 -lt ARG2: ARG1<ARG2

          • -lt : INTEGER1 is less than INTEGER2

        • ARG1 -ne ARG2: ARG!=ARG2

          • -ne : INTEGER1 is not equal to INTEGER2

      • if对字符串进行判断

        • -n string

          • 字符串长度不为零

        • -z string

          • 字符串长度为零

        • str1 = str2

        • str1 != str2

      • if对文件进行判断

        • FILE1 -ef FILE2

          • FILE1 and FILE2 have the same device and inode numbers

        • FILE1 -nt FILE2

          • FILE1 is newer (modification date) than FILE2

        • FILE1 -ot FILE2

          • -ot :FILE1 is older than FILE2

        • -b FILE:文件存在且是一个块设备文件

        • -c FILE:文件存在且是一个字符设备文件

        • -d FILE:文件存在且是一个目录设备文件

        • -f FILE:文件存在且是一个普通文件

        • -h\-L FILE:文件存在且为软链接文件

          • lin

        • -S FILE:文件存在且是一个套接字文件

        • -e FILE:文件存在

          • equal

        • -s FILE:文件存在且大小不为0

        • -p FILE:文件存在且是一个管道文件

        • -w FILE:文件存在且有可写权限

        • -r FILE:文件存在且有可读权限

        • -x FILE:文件存在且有可执行权限

    • case in分支结构

      • 格式

        • case $变量名 in 常量1) 语句 ;; 常量2) 语句 ;; ······ 常量n) 语句 ;; *) 语句 esac

          • $变量名

            • 通过输入的变量,进入不同的 “常量)”分支

          • ;;

            • 和C中break的作用相同,shell中必须写;; (除非是最后一个分支)

          • *)

            • 起到通配符的作用,可以通配所有情况 shell中*)分支必须是最后一条分支

      • 1):如果变量的值为1

      • 1|2|3|4): 值为1或2或3或4都走该分支

      • [0-9]):0-9中的值都走该分支 不能写两位数,都是对单字符的判断

      • 1?):1开头两个字符一个确定一个不确定的情况

    • 循环结构

      • while循环结构

        • 格式

          • while [ test语句 ] do 语句块 done

            • while [ test语句 ] == while test 表达式

            • [] 中输入的语句需要用空格与中括号隔开

      • for循环结构

        • shell格式1(类似C语言)

          • 类似于C语言的格式 for ((表达式1;表达式2;表达式3)) do 循环体 done

            • 执行逻辑和C语言一致

        • shell格式2(自己的格式)

          • for 变量名 in 字符串列表 do 循环体 done

            • 执行逻辑

              • 循环变量i从in后面提供的字符串列表中,按顺序取值

              • 循环次数和字符串列表中字符串的个数有关

              • 直到i把字符串列表中每一个字符串的值都获取结束后,循环结束,(i为获取的值)

        • 使用连续列表的情况

          • seq 起始值 间隔值 终止值

            • 终端回显起始值到终止值之间的数

            • 故使用时需用指令置换符

          • {1..3}

            • 在bash编译器中遍历1-3中的每一个数 可以用在for中,单独使用不能回显在终端

            • {起始值..终止值}

              • 间隔值默认为1

              • 中间只能写两个点

      • select···in循环结构

        • 格式

          • select 变量名 in 选项列表 do 语句块 done

        • 执行逻辑

          • 会在终端打印选项列表 用户需要根据选项前面的序号做出选择 选择后变量会获取到相应的值 如果用户不做选择,会再次打印选项列表 如果用户选错,获取到空值

        • 常和case语句使用

          • 在select···in语句中,嵌套case···in语句, 可以根据用户的不同选择,使用case···in完成不同的处理

      • 辅助控制关键字

        • break n

          • 跳出n层循环

        • continu n

          • 退出第n层本次循环

            • 退出n层本次循环,跳出n层循环时,只需要看第n层循环是否有下一次即可

    • shell中的函数

      • 格式:(function)函数名() { 函数体 return 返回值 }

        • function 可加可不加

        • shell中的函数仍然满足先定义后调用

        • shell函数中是否还有返回值,根据实际的实现来决定

        • 返回值只能是(0~255)

      • 调用函数

        • ()内必须为空,不能写任何内容

        • 直接通过函数名调用函数

          • 函数名

          • fun

        • 函数调用后其内部的定义变量才能被调用

      • 如何获取函数的外部参数

        • 如果函数需要外部传参

          • 函数名 参数1 参数2 参数3 ·····

          • fun 12 34

            • 调用函数fun

        • 通过外部传参获取两个数,计算两数和

          • 先调用函数,并输入外部参数

        • 函数内部仍然通过$获取外部参数

          • n大于等于10时需用${10}

        • 函数内部使用$1 $2

          • 获取12和23 两个外部参数

        • 在函数外可以访问函数内的变量(全局变量),但需要函数被调用后访问

        • 函数内和脚本内的外部参数获取互不影响

          • 在函数内使用位置变量,获取的是函数的外部参数

          • 在脚本中使用位置变量,获取的是脚本的外部参数

        • 如果想要在函数中,使用脚本的外部参数,只能通过函数调用将该参数传给函数

      • 如何获取函数的输出

        • 函数有返回值

          • $?

            • 只能获取0-255范围内的值

            • 获取的是上一条指令的运行结果

        • 函数没有返回值

          • 但是函数有echo输出,可以使用命令置换符获取

          • ·· $()

      • local

        • 修饰局部变量

          • local sum

          • 全局变量sum被修饰为局部变量

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

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

相关文章

【项目实训】后端逻辑完善

经测试&#xff0c;我们决定前端可以同时选择多个类型的岗位进行查询&#xff0c;以显示相应的公司岗位信息 于是&#xff0c;修改后端函数的逻辑&#xff1a; 后端 首先&#xff0c;因为要对checkList中的job_name进行模糊匹配查询&#xff0c;于是使用以下代码&#xff1a…

C++之STL(九)

1、函数对象 什么适合推荐使用函数对象&#xff1f; 需要状态的函数调用: 需要状态的函数调用: 函数对象可以包含成员变量&#xff0c;可以在多次调用中保持状态。这在某些算法中非常有用。 提高性能: 编译器可以更好地优化函数对象&#xff0c;因为它们是具体的类型&#xf…

[Redis]主从模式

启动主从复制 由于我们只有一台机器&#xff0c;所以我们只能在机器上开多个redis程序来演示不同的机器 因为一个端口号只能被一个进程绑定&#xff0c;所以我们需要修改配置&#xff0c;绑定不同的端口号&#xff0c;并且还要修改工作目录&#xff08;数据持久化的位置&#…

ChatTTS源码部署

感谢阅读 默认已完成的操作准备工作下载源码安装依赖下载补丁(报错在运行) 界面展示(discord上有各种补丁&#xff0c;我的加了UI补丁和音色增强)提示词常用&#xff08;这个每个音基本都能生效&#xff09;语调类语速类情感类 默认已完成的操作 python版本>3.9 cuda版本的…

3D渲染时如何提高GPU的使用率?这7点告诉你

GPU 正逐渐取代 CPU 在 3D 渲染中的地位。我们看到许多 GPU 渲染器如 Redshift、Octane、FStorm 等不断推出。以前只支持 CPU 渲染的渲染器&#xff0c;如 Arnold、V-Ray、Renderman、Keyshot 等&#xff0c;现在也开始支持 GPU 渲染。实时渲染的发展使 GPU 更受欢迎&#xff0…

梗图生成器突然爆红;ElevenLabs发布IOS APP 高质量语音朗读手机各种文本内容;开源工作流架构ControlFlow

✨ 1: 梗图生成器 fabianstelzer 在Glif做的一个超强meme生成器 Glif 是一个工作流&#xff0c;能生成文字图片和视频&#xff0c;用工作流的形式可以完成很多的花样来。 最近爆红的梗图生成器&#xff0c;WOJAK MEME GENERATOR &#xff0c;也是用工作流的形式来生成这些有…

TiDB-从0到1-数据导出导入

TiDB从0到1系列 TiDB-从0到1-体系结构TiDB-从0到1-分布式存储TiDB-从0到1-分布式事务TiDB-从0到1-MVCCTiDB-从0到1-部署篇TiDB-从0到1-配置篇TiDB-从0到1-集群扩缩容 一、数据导出 TiDB中通过Dumpling来实现数据导出&#xff0c;与MySQL中的mysqldump类似&#xff0c;其属于…

如何选择适合你的免费电子合同软件?八款工具深度对比

主流的8款免费合同软件包括&#xff1a;国内的e签宝、法大大、上上签、契约锁&#xff0c;以及国外的SignWell、PandaDoc、Signaturely、HelloSign和SignRequest。 随着技术的进步&#xff0c;尤其是区块链技术的应用&#xff0c;电子合同的安全性和可信度正在逐渐增强。这些技…

如何提取mac app中的应用程序图标 x.app图标位置

在macos系统中安装的应用程序 .app的图标都是 以 .icns结尾的&#xff0c;默认位于 .app应用程序包中的Contents/Resources/目录下&#xff0c;只要是在这个目录下的 .icns文件就是这个应用的图标&#xff0c;如&#xff1a;mac版微信的图标就是 /Applications/WeChat.app/Co…

5个顶级开源Agent框架,你必须知道!

进入2024年&#xff0c;人工智能的发展已经达到了前所未有的高度&#xff0c;尤其是在Agent框架这一领域&#xff0c;出现了几个引人注目的技术成果。这些框架在智能规划、用户体验增强、记忆处理、以及大型模型调用等方面有着卓越表现&#xff0c;对AI界的未来发展提供了值得期…

利用多模态大模型,构建自动驾驶场景检索解决方案 | 创新场景

ITValue 痛点 在自动驾驶数据闭环的业务场景中&#xff0c;企业面临的挑战是难以高效的从PB级的视频和图片中选取有价值的数据&#xff0c;以训练和优化自动驾驶算法。 解决方案 为解决该挑战&#xff0c;亚马逊云科技利用大语言模型和图像文本多模态嵌入空间架构&#xff0c;构…

CY5-NHS生物标记应用146368-14-1

在生物科学研究和技术应用领域&#xff0c;荧光标记技术已成为一种科研工具。其中&#xff0c;CY5-NHS以其荧光特性和标记能力&#xff0c;在生物标记应用中扮演着科研角色。 CY5-NHS的特性与优势 CY5-NHS是一种荧光标记试剂&#xff0c;其荧光基团CY5赋予其强烈的荧光信号和…

【vue3】【vant】 移动本草纲目案例发布收藏项目源码

更多项目点击&#x1f446;&#x1f446;&#x1f446;完整项目成品专栏 【vue3】【vant】 移动本草纲目案例发布收藏项目源码 获取源码方式项目说明&#xff1a;其中功能包括 项目包含&#xff1a;项目运行环境文件截图 获取源码方式 加Q群&#xff1a;632562109项目说明&am…

flink的窗口

目录 窗口分类 1.按照驱动类型分类 1. 时间窗口&#xff08;Time window&#xff09; 2.计数窗口&#xff08;Count window&#xff09; 2.按照窗口分配数据的规则分类 窗口API分类 API调用 窗口分配器器&#xff1a; 窗口函数 增量聚合函数&#xff1a; 全窗口函数…

llamafactory-llama3微调中文数据集

一、定义 https://github.com/SmartFlowAI/Llama3-Tutorial/tree/main 基准模型测试opencompass 离线测评数据准备微调训练合并测试人工审核对比 二、实现 基准模型测试 基准模型 llama3-8b https://zhuanlan.zhihu.com/p/694818596? https://github.com/SmartFlowAI/Llam…

什么样的台灯适合学生使用?五款暑假必入护眼大路灯分享

什么样的台灯适合学生使用&#xff1f;现在近视越来越低龄化&#xff0c;戴眼镜的小朋友越来越多&#xff0c;每每看着自己孩子眼睛贴到作业本上写作业&#xff0c;我的心都会提到嗓子眼。去医院一检查&#xff0c;果然&#xff0c;远视储备即将告罄&#xff0c;必须要防护了&a…

深度剖析:前端如何驾驭海量数据,实现流畅渲染的多种途径

文章目录 一、分批渲染1、setTimeout定时器分批渲染2、使用requestAnimationFrame()改进渲染2.1、什么是requestAnimationFrame2.2、为什么使用requestAnimationFrame而不是setTimeout或setInterval2.3、requestAnimationFrame的优势和适用场景 二、滚动触底加载数据三、Elemen…

【项目实训】解决前后端跨域问题

由于前端框架使用vue&#xff0c;后端使用flask&#xff0c;因此需要解决前后端通信问题 在vue.config.js中修改 module.exports defineConfig({transpileDependencies: true,lintOnSave:false, }) // 跨域配置 module.exports {devServer: { //记住&#x…

2024 年适用于 Windows 11/10/8/7 的最佳 SSD 磁盘克隆软件

磁盘克隆软件对于用户在发生数据灾难时保证数据/系统安全至关重要。克隆软件可以创建驱动器的副本并保持数据相同。如果发生数据灾难&#xff0c;您可以设置克隆驱动器以克隆回数据/驱动器。或者您可以直接使用克隆的驱动器继续工作。 除了传统的 HDD&#xff0c;Windows 11/1…

使用nvm切换node版本时报错:exit status 1解决办法

作者介绍&#xff1a;计算机专业研究生&#xff0c;现企业打工人&#xff0c;从事Java全栈开发 主要内容&#xff1a;技术学习笔记、Java实战项目、项目问题解决记录、AI、简历模板、简历指导、技术交流、论文交流&#xff08;SCI论文两篇&#xff09; 上点关注下点赞 生活越过…