一、shell基本知识
Ⅰ、为什么要学习和使用shell编程
通过编程,简化日常的维护工作,使得管理员从简单的重复劳动解脱出来
Ⅱ、什么是shell
shell的功能
Shell又称命令解释器,它能识别用户输入的各种命令,并传递给操作系统。它的作用类似于Windows操作系统中的命令行,但是,Shell的功能远比命令行强大的多。在UNIX或者localhost中,Shell既是用户交互的界面,也是控制系统的脚本语言。
shell的分类
Bourne Shell:标识为sh,该Shell由Steve Bourne在贝尔实验室时编写。在许多Unix系统中,该Shell是root用户的默认的Shell。
Bourne-Again Shell:标识为bash,该Shell由Brian Fox在1987年编写,是绝大多数localhost发行版的默认的Shell。
Korn Shell:标识为ksh,该Shell由贝尔实验室的David Korn在二十世纪八十年代早期编写。它完全向上兼容 Bourne Shell 并包含了C Shell 的很多特性。
C Shell:标识为csh,该Shell由Bill Joy在BSD系统上开发。由于其语法类似于C语言,因此称为C Shell。
查看当前系统支持的shell?
[root@localhost ~]# cat /etc/shells
查看当前系统支持的shell?
[root@localhost ~]# echo $SHELL
Ⅲshell脚本的书写规范
-
通常情况下,我们会给shell脚本起名为filename.sh
-
第一行写声明,声明当前的shell脚本使用哪个命令解释器:#!/bin/bash
-
除了第一行以外,以#开头的行都为注释
-
shell脚本的作者
-
shell脚本的创建时间
-
脚本的作用,命令的说明
-
#编辑.sh文件时自动生成关于脚本的注释
[root@localhost ~]# cat /root/.vimrc
#用vim创建新文件会自动生成脚本文件的注释
注:用touch命令创建不会自动生成脚本文件的注释
Ⅳ、shell脚本的执行方式
①交互式执行
[root@localhost ~]# for filename in `ls /etc`
> do
> if echo "$filename" | grep "passwd"
> then
> echo "$filename"
> fi
> done
②作为程序文件执行(常用)
对于一组需要经常重复执行的Shell语句来说,将它们保存在一个文件中来执行。我们通常称这种包 含多个Shell语句的文件为Shell脚本,或者Shell脚本文件。脚本文件是普通的文本文件,可使用任何的 文本编辑器查看或修改Shell脚本。
[root@localhost ~]# mkdir /test
[root@localhost ~]# cd /test
[root@localhost test]# vim test1.sh
#!/bin/bash
#########################
#File name:test1.sh
#Version:v1.0
#Email:admin@test.com
#Created time:2024-11-02 14:56:01
#Description:
#########################
for filename in `ls /etc`
doif echo "$filename" | grep "passwd"thenecho "$filename"fi
done
Ⅴ、实行脚本的方法
①bash ./filename.sh(产生子进程,再运行,使用当前指定的bash shell去运行)
②./filename.sh(产生子进程,再运行,使用脚本里面指定的shell去运行。使用该种方式执行需要x权限)
③source ./filename.sh(source命令是一个shell内部命令,其功能是读取指定的shell程序文件,并且依次执行其中的所有的语句,并没有创建新的子shell进程,所以脚本里面所有创建的变量都会保存到当前的shell里面)
④. ./filename.sh(和source一样,也是使用当前进程执行)
示例:
[root@localhost test]# vim test2.sh
#!/bin/bash
#########################
#File name:test2.sh
#Version:v1.0
#Email:admin@test.com
#Created time:2024-11-02 15:14:39
#Description:
#########################
cd /tmp
pwd
注:执行shell脚本时,如果使用1和2这种方式执行会在当前的进程下产生一个新的bash子进程,所以子进程切换到了/tmp目录,当脚本结束,子进程也就结束了,所以当前进程的目录不会发生变化;3和4方式执行时,不会产生新的进程,所以脚本执行结束后当前的目录会变成/tmp
[root@localhost tmp]# cd - 返回上一级目录
Ⅵ、shell脚本的退出状态码
-
在UNIX或者Linux中,每个命令都会返回一个退出状态码。退出状态码是一个整数,其有效范围为0~255。通常情况下,成功的命令返回0,而不成功的命令返回非0值。非0值通常都被解释成一个错误码。行为良好的UNIX命令,程序和工具都会返回0作为退出码来表示成功。
-
Shell脚本中的函数和脚本本身也会返回退出状态码。在脚本或者是脚本函数中执行的最后的命令会决定退出状态码。另外,用户也可以在脚本中使用exit语句将指定的退出状态码传递给Shell。
-
可以使用exit num指定脚本的退出状态码。
[root@localhost ~]# echo $? 查看上一条命令的状态码
上一条命令执行成功状态码为0;执行失败为2
二、shell的变量
Ⅰ、什么是变量
变量就是程序设计语言中可以变化的量,本质上来讲,变量就是在程序中保存用户数据的一块内存空间。而变量名就是这块内存空间的地址。
Ⅱ、变量的命令
-
可以使用数字、字母和下划线给变量命名
-
不能用数字开头
-
如果给同一个变量赋值多次,最后一次赋值会覆盖之前的值
合法的变量名:name、NAME、name_1、Name_1
不合法的变量名:1name、name*1、name_1%
Ⅲ、查看变量的值
-
查看单个变量的
[root@localhost ~]# uid=123 定义一个变量
[root@localhost ~]# echo $uid
123
[root@localhost ~]# echo ${uid}
123
[root@localhost ~]# printf "$uid\n"
123
[root@localhost ~]# printf "${uid}\n"
123
如果后两种方式不加\n
[root@localhost ~]# printf "$uid"
123[root@localhost ~]#
查看多个变量的值
-
set:查看所有的变量和函数
-
declare:查看所有的变量和函数
-
env:显示所有的全局变量
Ⅳ、变量的定义
-
在命令行中定义:退出当前进程后该变量就失效,其他终端上无法使用该变量
-
在文件中定义:永久生效
-
当前用户生效的文件
~/.bashrc 和~/.bash_profile
-
所有用户生效的文件
/etc/bashrc、/etc/profile、/etc/profile.d/*.sh
-
su和su - 切换方式加载的文件不同
Ⅴ、变量的分类
Ⅵ、取消变量
[root@localhost etc]# unset var
Ⅶ、变量运算
实验:计算用户输入的任意两个整数和、差、乘积、商、余数
方法一:
[root@localhost test]#vim mkdir test4.sh
#!/bin/bash
#########################
#File name:test3.sh
#Version:v1.0
#Email:admin@test.com
#Created time:2024-11-02 16:13:53
#Description:
#########################
a=$1
b=$2
echo a+b=$((a+b))
echo a-b=$((a-b))
echo a*b=$((a*b))
echo a/b=$((a/b))
echo a%b=$((a%b))
方法二:
#!/bin/bash
#########################
#File name:test3.sh
#Version:v1.0
#Email:admin@test.com
#Created time:2024-11-02 16:13:53
#Description:
#########################
read -p "please input tow number:" a b
echo $a+$b=$(($a+$b))
echo $a-$b=$((a-b))
echo $a*$b=$((a*b))
echo $a/$b=$((a/b))
echo $a%$b=$((a%b))
示例:截取字符串
[root@localhost test]# str1="I love RHCE" 定义变量
[root@localhost test]# echo ${str1} 返回变量内容
I love RHCE
[root@localhost test]# echo ${#str1} 返回变量长度
11
[root@localhost test]# echo ${str1:1} 从I之后截取搭到结束
love RHCE
[root@localhost test]# echo ${str1:1:3} 从I之后截取三位
lo
[root@localhost test]# echo ${str1::3} 指定长度,不指定索引位置从头开始
I l