shell脚本基础之详解基本脚本的构建(一)

  • 在学习下述内容之前,默认我们是已经了解Linunx系统和有关基础命令,才开始学习shell编程的。在我们开始编写自己的shell脚本之前,需要我们必须了解一些预备知识,此篇博客会介绍shell脚本的预备知识

使用多个命令

  • 在此之前,我们输入Linux命令都是,输入一条命令,等待系统的输出,或进入此命令的内部环境,几乎没有同时操作多条命令的手段
  • shell脚本的关键在于输入多个命令并处理每个命令的结果,甚至可以将一个命令的结果传给另一个命令。shell可以将多个命令串起来,一次执行完成。如果两个命令需要一起运行,可以将它们放在同一行中,彼此用分号(;) 隔开。如下:
date;who

在这里插入图片描述

  • 如果你也完成了上述命令,那么你已经编写好了一个脚本。上述的简单脚本只用到了两个bash shell命令,date命令先运行,显示当前日期和时间,后面紧跟着who命令的输出,显示当前是那个用户登录在系统上。使用这种办法就能将任意的多个命令串联在一起,只要不超过最大命令行字符数255就行
  • 上述的分号分隔技术对于一些简单脚本尚可,但它也是有很大的缺陷:需要在每次运行之前,在命令行中输入整个命令,可以将这些命令组合成一个简单的文本文件,这样就不需要每次在命令行手动输入了。在需要运行这些命令时,只用运行这个文本文件即可

创建shell脚本文件

  • 在创建shell脚本文件时,必须在文件的第一行指定要使用的shell,格式如下:
#!/bin/bash
  • 在大部分的shell脚本中,#(井号)用作注释行,shell并不会处理shell脚本中的注释行。但是,shell脚本的第一行是个例外,#后面的!会指定使用哪个shell来运行脚本,你可以使用bash shell,也可以指定使用另一类型的shell来运行你的脚本
  • 在指定了shell之后,就可以在文件的每一行中输入命令,也可以使用#来添加注释。如下:
  #!/bin/bash
  # 输出当前时间及登陆系统的用户
  date
  who

在这里插入图片描述

  • 上述就是当前脚本的所有内容了,可以根据需要将两个命令放在同一行上,但在shell脚本中你可以将命令书写在每一个独立的行中,shell会根据命令在文件中出现的顺序进行处理
  • 还有,在当前脚本的第二行也是以#开头来添加注释,shell不会解释以#开头的行(除了以#!开头的第一行),此注释的作用仅仅只是说明当前脚本是要做什么,当很久之后我们回头看此脚本,可以通过此注释来了解脚本的作用
  • 将此脚本保存在名为test1的文件中,然后运行脚本:
    在这里插入图片描述
  • 结果是未找到当前test1的命令,开头不顺利呀!!
  • 我们现在要解决的问题就是让bash shell能找到你的脚本文件,前置知识:shell会通过PATH环境变量来查找命令,快速查看PATH环境变量,如下:
echo $PATH

在这里插入图片描述

  • PATH环境变量为一组目录, shell只会在PATH变量中展示的目录来查找脚本,要让shell找到test1脚本,只需使用一下两种方法:
    • 将shell脚本文件所处的目录添加到PATH环境变量中
    • 在提示符中用绝对或相对文件路径来引用shell脚本文件

注意:

  • 一些Linux发行版将$HOME/bin目录添加进了PATH环境变量。它在每个用户的HOME目录下提供了一个存放文件的地方,shell可以在那里查找要执行的命令

  • 上述问题,不推荐使用使用第一种方法,因为我们不能保证每次运行shell脚本都是在此添加到PATH环境变量的目录,每次在一个新的目录中运行shell脚本,都将目录添加到PATH环境变量吗?这样做是不现实的

  • 我们采用第二种方法,将脚本文件的确切位置告诉shell,为了引用当前目录下的文件,可以使用.操作符,如下:

./test1

在这里插入图片描述

  • 裂开,还是没有运行成功,它告诉我们我们当前用户没有文件的执行权限,快速查看当前文件的权限就能找到此问题的所在:
ll test1

在这里插入图片描述

  • 在创建test1文件时,umask的值决定了新文件的默认权限设置,在我们当前使用的Ubuntu 20.04中umask值被默认设置成了022,所以系统创建的文件是对于属主来说是没有执行权限的,使用chmod命令赋予文件属主执行权限:
chmod u+x test1
./test1

在这里插入图片描述

  • 如上显示,此脚本已经执行成功了!!!

显示消息

  • 大多数shell命令都是换产生自己的输出,这些输出会显示在脚本所运行的控制台上,很多时候,我们可能想要告诉用户当前脚本正在做什么,可以使用echo命令来实现这一点,如果在echo命令后面加上一个字符串,该命令就会在当前控制台输出显示当前字符串
echo 输出当前时间及登陆系统的用户

在这里插入图片描述

  • 默认情况,是不需要使用引号将要显示文本字符串标注出来,但是有时在字符串中出现引号就比较麻烦了
    在这里插入图片描述

  • echo命令可用单引号或双引号来划定文本字符串。如果在字符串中用到了它们,你需要在文本中使用其中一种引号,而用另外一种来将字符串划定起来
    在这里插入图片描述

  • 可以将echo语句添加到shell脚本的任何位置以此来显示需要额外展示的信息
    在这里插入图片描述

  • 执行脚本如下输出:
    在这里插入图片描述

  • 如果你想要将当前文本信息与命令的输出显示在同一行中,需要如何做?可以使用echo -n来实现。如下:
    在这里插入图片描述

  • 如下输出:
    在这里插入图片描述

  • echo命令是shell脚本和用户交互的重要工具,在很多地方我们都会使用到它,尤其是需要显示脚本变量的值的时候,下面会介绍!!

使用变量

运行shell脚本中的单个命令自然有用,但是有自身的限制。通常你会需要在shell命令使用其他数据来处理信息。可以通过变量来实现。变量允许你临时性地将信息存储在shell脚本中,以便和脚本中的其他命令一起使用

环境变量

  • 环境变量,用来记录特定的系统信息。比如系统的名称、登录到系统上的用户名、用户的系统ID(也称为UID)、用户的默认主目录以及shell查找程序的搜索路径。可以用set命令来显示一份完整的当前环境变量列表
set

在这里插入图片描述

  • 上图并未将所有的的环境变量展示出来!!
  • 在脚本中,你可以在环境变量名称之前加上美元符($)来使用这些环境变量,如下展示:
#!/bin/bash
# 展示系统用户信息
echo 用户名:$USER
echo 用户ID:$UID
echo 用户家目录:$HOME

在这里插入图片描述

  • 注意,echo命令中的环境变量会在脚本运行时替换成当前值。另外,在第一个字符串中可以将$USER系统变量放置到双引号中,而shell依然能够知道我们的意图。但采用这种方法也还有一个问题,如下:
echo 衬衫的价格是 $99

在这里插入图片描述

  • 显然这并不是我们想要的。只要shell脚本在引号中出现美元符,它就会以为你在引用一个变量。在上述例子中,脚本会尝试显示变量$9(但并未定义),再显示数字9。要显示美元符,你必须在$前面放置一个反斜线\,来进行转义

在这里插入图片描述

  • 反斜线在shell脚本将美元符转义为实际的美元符,而不是变量
注意:
  • 你可能还见过通过${variable}形式引用的变量。变量名两侧额外的花括号通常用来帮助识别美元符后的变量名

用户变量

  • 除了环境变量,shell脚本还允许在脚本中定义和使用用户的变量。定义变量允许临时存储数据并在整个脚本中使用,从而使shell脚本看起来更像一个真正的计算机程序

  • 用户变量可以是任何由字母、数字或下划线组成的文本字符串,长度不超过20个。用户变量区分大小写,所以变量Var1和变量var1是不同的

  • 使用等号将值赋给用户变量。一定注意(重要的事要说三遍!!!):

    • 在变量、等号和值之间不能出现空格
    • 在变量、等号和值之间不能出现空格
    • 在变量、等号和值之间不能出现空格
  • shell脚本会自动决定变量值的数据类型。在脚本的整个生命周期里,shell脚本中定义的变量会一直保持着它们的值,但在shell脚本结束时会被删除掉,与系统变量类似,用户变量可通过美元符引用,如下展示:

#!/bin/bash
name=wy
age=18
echo 我是$name 今年$age
name=fbl
echo 我是$name 今年也$age

在这里插入图片描述

命令替换

  • shell脚本中最有用的特性之一就是可以从命令输出中提取信息,并将其赋给变量。把输出赋给变量之后,就可以随意在脚本中使用了。这个特性在处理脚本数据时尤为方便
  • 有两种方法可以将命令输出赋给变量:
    • 反引号字符(`)
    • $()格式
  • 要注意反引号字符,这可不是用于字符串的那个普通的单引号字符。由于在shell脚本之外很少用到,你可能甚至都不知道在键盘什么地方能找到这个字符。但你必须慢慢熟悉它,因为这是许多shell脚本中的重要组件。提示:在美式键盘上,它通常和波浪线(~)位于同一键位
  • 命令替换允许你将shell命令的输出赋给变量,要么用一对反引号把整个命令行命令围起来,要么使用$()格式:
testing=`date`
testing=$(date)
  • shell会运行命令替换符号中的命令,并将其输出赋给变量testing。注意,赋值等号和命令替换字符之间没有空格,如下展示:
#/bin/bash
testing01=`date`
testing02=$(date)
echo 以下是使用两种方法
echo 方法1 $testing01
echo 方法1 $testing02

在这里插入图片描述

  • 再举一个例子:在脚本中通过命令替换获得当前日期并用它来生成唯一文件名
#!/bin/bash
# 将/usr/bin目录下的文件重定向到log文件中
today=$(date +%y%m%d)
ls /usr/bin -al > log.$today

在这里插入图片描述

  • today变量是被赋予格式化后的date命令的输出。提取日期信息来生成日志文件名常用的一种技术。+%y%m%d格式告诉date命令将日期显示为两位数的年月日的组合
    在这里插入图片描述
  • 这个脚本将日期值赋给一个变量,之后再将其作为文件名的一部分。文件自身含有目录列表的重定向输出。运行该脚本之后,应该能在目录中看到一个新文件
    在这里插入图片描述
  • 目录中出现的日志文件采用$today变量的值作为文件名的一部分。日志文件的内容是/usr/bin目录内容的列表输出。如果脚本在明天运行,日志文件名会是log.230404,就这样为新的一天创建一个新文件
注意
  • 命令替换会创建一个子shell来运行对应的命令。子shell(subshell)是由运行该脚本的shell所创建出来的一个独立的子shell(child shell)。正因如此,由该子shell所执行命令是无法使用脚本中所创建的变量的
  • 在命令行提示符下使用路径./运行命令的话,也会创建出子shell;要是运行命令的时候不加入路径,就不会创建子shell。如果你使用的是内建的shell命令,并不会涉及子shell。在命令行提示符下运行脚本时一定要留心
评论 2
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值