第二十二章 Shell脚本入门

article/2025/6/7 15:14:31

第二十二章 Shell脚本入门

Shell脚本就是包含一系列命令的文件。Shell读取该文件并执行其中的命令,Shell的独特之处在于它即使系统强大的命令接口,又是脚本语言解释器。

创建并执行Shell脚本

创建并执行脚本,要做到3件事:

  1. 编写脚本。
  2. 将脚本设置为可执行。
  3. 把脚本放在Shell能够找到的地方。

脚本文件格式


沿袭传统,写编写一个“Hello World”的脚本。打开文本编辑器,输入下列脚本:

#!/bin/bash

# 这是我的第一个Shell脚本

echo ‘Hello World!’



脚本的第一行表明这是一个bash脚本,第二行是一个注释,第三行通过echo命令打印Hello World。

在Shell脚本中,注释可以出现在代码行尾,只要之前至少有一个空白字符即可,例如:


echo ‘Hello World!’ # 这也是注释



代码行内的#之后的内容都是注释,同样也适用于命令行。

echo "Hello World!" # 这也是注释

输出结果如下:

Hello World!



脚本的第一行开头的字符序列#!是一种名为shebag的特殊构件。shebang用于告知内和该使用那个解释器执行接下来的脚本。所有的Shell脚本都应该将其作为第一行。

可执行权限

shell脚本文件默认没有执行权限,不能使用,需要增加执行权限。使用chmod命令来实现。

chmod 755 hello_world.sh #设置hello_world.sh的权限码为755ls -l hello_world.sh #列出hello_world.sh的长格式信息

命令输出如下:

外链图片转存失败,源站可能有防盗链机制,建议将图片保存下来直接上传

脚本位置

设置好权限就可以执行脚本了。

外链图片转存失败,源站可能有防盗链机制,建议将图片保存下来直接上传

要想执行脚本,必须在脚本名称之前指定路径。如果不这么做,会得到如下结果:

外链图片转存失败,源站可能有防盗链机制,建议将图片保存下来直接上传


因为脚本所在的位置,没有保存在PATH环境变量中。PATH的值是以冒号分隔的目录列表,可以查看PATH的内容:

echo $PATH

PATH内容如下图:

外链图片转存失败,源站可能有防盗链机制,建议将图片保存下来直接上传

可以看到多个目录,如果脚本位于其中任何一个目录就可以直接通过文件名执行。大多数Linux发行版会在PATH变量中加入用户主目录下的bin目录,以便用户执行自己程序。如果创建了bin目录并将脚本置于其中,它就能其他程序一样直接执行了。

如果PATH变量没有包含该目录,可以自己手动添加,把下面这行加入.bashrc文件中即可:


export PATH=~/bin:“$PATH”



改动会在每个新的终端会话中生效。要想将改动应用于当前终端会话,必须让Shell重新读取.bashrc文件。可以通过sourcing操作实现。

. .bashrc


点好命令是source命令的同义词,该内建命令读取指定Shell命令文件,将其中的命令视为直接从键盘输入的命令。


注意: 对于Ubuntu(还有多数基于debian的操作系统),在执行用户的.bashrc文件时,如果/bin目录已存在,则自动将其添加到PATH变量中。在Ubuntu中创建好/bin目录,然后注销,再重新登录,一切就当妥当了。


脚本的理想位置

~/bin目录是一个存放个人脚本的理性位置。如果编写了一个系统所有用户都可以使用的脚本,呢吗这类脚本的传统存放位置是/usr/local/bin。超级用户使用的脚本通常放置在/usr/local/sbin。在大多数情况下,本地提供的软件,无论是脚本或者是编译好的程序,都应该放置在/usr/local中,而非/bin或/usr/bin中。这些目录都是由Linux文件系统层次结构标准规定的,只能包含由Linux发行商提供和维护的文件。

更多的格式技巧

编写脚本要考虑的脚本的可维护性,让脚本易读易理解是增强其可维护性的一种方法。

长选项

很多命令都支持短选项和长选项。例如,ls命令的众多选项,即可用短选项表示,也可以用长选项表示:

ls -ad

等价于:

ls --all --directory

为了减少输入,在命令行上输入时采用短选项,在编写脚本时,长选项可以增强可读性。

缩进与续行

当使用冗长的命令时,可以将命令分散写成多行,以此增强可读性。以find命令作为示例。

find playground \( -type f -not -perm 0600 -exec chmod 0600 '{}' ';' \) -or \( -type d -not -perm 0700 -exec chmod 0700 '{}' ';' \)

显然该命令,不易看出其含义。在脚本中,将其改写成下面这种形式,会更容易理解:
find playground \\( \-type f \-not -perm 0600 \-exec chmod 0600 '{}' ';' \\) \-or \\( \-type d \-not -perm 0700 \-exec chmod 0700 '{}' ';' \\) \

利用续行和缩进,能够更清晰地描述这个复杂命令背后的逻辑。该技术也适用于命令行,不过很少用到,因其不便于输入和编辑。脚本和命令的一个区别是,脚本可以使用制表符来实现缩进,而命令行却无法实现,因为按Tab键会激活自动补齐功能。

脚本编写用到的Vim配置功能

启用语法高亮:


:syntax on



启用查找结果高亮:

:set hlsearch



设置制表符占用的列数:

:set tabstop=4


默认值是8,将列数设置为4(这是一种常见的做法)便于较长的行适应屏幕。

启用“自动缩进”特征:


:set autoindent



这个选项会使Vim在缩进新行的时候与上一行保持一致。这能够加快很多编程构建的输入速度。按Ctrl-D组合键可以停止缩进。

将这些命令(不包括开头的冒号)加入你的~/.vimrc文件,就能使改动永久有效。



http://www.hkcw.cn/article/BNfrQHFBFk.shtml

相关文章

Pandas取代Excel?

有人在知乎上提问:为什么大公司不用pandas取代excel? 而且列出了几个理由:Pandas功能比Excel强大,运行速度更快,Excel除了简单和可视化界面外,没有其他更多的优势。 有个可怕的现实是,对比Exce…

网络安全运维实训室建设方案

一、网络安全运维人才需求与实训困境 在数字化时代,网络安全已成为国家安全、社会稳定和经济发展的重要基石。随着信息技术的飞速发展,网络安全威胁日益复杂多样,从个人隐私泄露到企业商业机密被盗,从关键基础设施遭受攻击到社会…

【C++篇】STL适配器(下篇):优先级队列与反向迭代器的底层奥秘

💬 欢迎讨论:在阅读过程中有任何疑问,欢迎在评论区留言,我们一起交流学习! 👍 点赞、收藏与分享:如果你觉得这篇文章对你有帮助,记得点赞、收藏,并分享给更多对C感兴趣的…

在使用十字滑台的过程中,我们需要注意哪些关键事项呢

在使用十字滑台的过程中,需要注意以下关键事项: 安全操作:在使用十字滑台时,务必要注意安全,戴好手套和护目镜,避免发生意外伤害。 稳定支撑:确保十字滑台稳固地放置在平坦稳定的表面上&#x…

【笔记】用命令手动下载并安装 tokenizers 库.whl文件(Python 3.12+)

Python 3.12 虚拟环境中安装 tokenizers 教程笔记 在 Python 3.12 虚拟环境中安装 tokenizers 库时,我们可能会遇到pip install tokenizers安装失败和找不到适配版本的公开 whl 文件,从而导致tokenizers库缺失的问题。 经过探索,我们找到了…

光子器件仿真软件基础与基于优化方法的器件逆向设计---案例片上米散射结构色超构表面单元仿真

以下为针对片上米散射结构色超构表面单元仿真的技术要点和方法整理: 仿真流程框架 import meep as mp import numpy as np # 创建超构表面单元模型 cell_size mp.Vector3(1, 1, 0) geometry [mp.Cylinder(height0.5, radius0.2, materialmp.Medium(index3.5))] …

软件工程的定义与发展历程

文章目录 一、软件工程的定义二、软件工程的发展历程1. 前软件工程时期(1940s-1960s)2. 软件工程诞生(1968)3. 结构化方法时期(1970s)4. 面向对象时期(1980s)5. 现代软件工程(1990s-至今) 三、软件工程的发展趋势 一、软件工程的定义 软件工程是应用系统化、规范化、可量化的方…

基于SDN环境下的DDoS异常攻击的检测与缓解

参考以下两篇博客,最后成功: 基于SDN的DDoS攻击检测和防御方法_基于sdn的ddos攻击检测与防御-CSDN博客 利用mininet模拟SDN架构并进行DDoS攻击与防御模拟(Ryumininetsflowpostman)_mininet模拟dos攻击-CSDN博客 需求 H2 模拟f…

VS下C++及C#项目打包发布方法

一.打包为单一exe文件 1.打开项目属性页(右键项目 → 属性) 2.选择配置(如 Release) 3.项目属性→ C/C → 代码生成→ 运行库 将 运行时库(Runtime Library) 设置为: /MT(Release 模…

【免费】2004-2020年各省电力消费量数据

2004-2020年各省电力消费量数据 1、时间:2004-2020年 2、来源:国家统计局、统计年鉴 3、指标:行政区划代码、地区、年份、电力消费量(亿千瓦小时) 4、范围:31省 5、指标说明:电力消费量是指在一定时期内&#xff…

[Python] python信号处理绘制信号频谱

python信号处理绘制信号频谱:scipy.signal.welch 文章目录 python信号处理绘制信号频谱:scipy.signal.welch一、函数介绍二、核心参数详解三、返回值四、算法原理五、关键特性六、完整示例七、应用场景推荐配置八、常见问题解决九、与FFT方法的对比 scip…

【图像处理入门】4. 图像增强技术——对比度与亮度的魔法调节

摘要 图像增强是改善图像视觉效果的核心技术。本文将详解两种基础增强方法:通过直方图均衡化拉伸对比度,以及利用伽马校正调整非线性亮度。结合OpenCV代码实战,学会处理灰度图与彩色图的不同增强策略,理解为何彩色图像需在YUV空间…

Mybatis--创建mapper接口

创建mapper接口 MyBatis中的mapper接口相当于以前的dao(原来的dao是有dao的接口以及dao的实现类)。但是区别在于,mapper仅仅是接口,我们不需要提供实现类。因为我们的mybatis里面有面向接口编程,只需要创建mapper接口…

vue3:Table组件动态的字段(列)权限、显示隐藏和左侧固定

效果展示 根据后端接口返回&#xff0c;当前登录用户详情中的页面中el-table组件的显示隐藏等功能。根据菜单id查询该菜单下能后显示的列。 后端返回的数据类型: 接收到后端返回的数据后处理数据结构. Table组件文件 <!-- 自己封装的Table组件文件 --> onMounted(()>…

力扣HOT100之多维动态规划:1143. 最长公共子序列

这道题之前刷代码随想录的时候做过&#xff0c;但是现在又给忘干净了&#xff0c;这道题需要用二维dp数组来做&#xff0c;看了一下自己当时写的博客&#xff0c;一下子就看懂了。这道题的子序列可以不连续&#xff0c;所以dp数组的定义和最长重复子数组不一样&#xff0c;我总…

无锁队列—C++内存序最佳实践

叙述方式&#xff1a; 1.背景介绍 &#xff08;使用场景&#xff09; 2.讲结论 (无锁队列实现) 3.讲内存序的使用&#xff08;通用方式&#xff09; 一、背景 本文通过一个“单生产者-单消费者”模型的场景&#xff0c;讲解基于C原子操作和内存序实现的无锁队列 在生产者…

ADC模数转换控制

目录 1. Convst信号的功能本质 1.1 核心作用 1.2 关键优势 1.3 Convst与SPI接口的协作关系 2.实际设计要点 2.1 硬件连接方案 2.2 时序约束&#xff08;以AD7685为例&#xff09; 2.3 多片ADC同步策略 3.高级应用技巧 3.1 动态调整采样率 3.2 抗干扰设计 3.3 故障排查 4.总…

QT常用控件(1)

控件是构成QT的基础元素&#xff0c;例如Qwidget也是一个控件&#xff0c;提供了一个‘空’的矩形&#xff0c;我们可以往里面添加内容和处理用户输入&#xff0c;例如&#xff1a;按钮&#xff08;QpushButton&#xff09;&#xff0c;基础显示控件&#xff08;Lable&#xff…

Linux系统-基本指令(5)

文章目录 mv 指令cat 指令&#xff08;查看小文件&#xff09;知识点&#xff08;简单阐述日志&#xff09;more 和 less 指令&#xff08;查看大文件&#xff09;head 和 tail 指令&#xff08;跟查看文件有关&#xff09;知识点&#xff08;管道&#xff09;时间相关的指令&a…

C 语言学习笔记(预处理和库文件)

内容提要 预处理库文件 预处理 预处理编译汇编链接 什么是预处理 预处理就是在源文件&#xff08;.c文件&#xff09;编译之前&#xff0c;所进行的一部分预备操作&#xff0c;这部分操作是由预处理器&#xff08;预处理程序&#xff09;自动完成。当源文件在编译时&#x…