Shell学习总结

Shell的执行方式

作为可执行程序

1
2
chmod +x run.sh			# 为脚本添加执行权限
./run.sh				# 执行脚本

注意:

  • 此种写法需在脚本第一行指定执行器,例如#!/bin/bash
  • 此种方式执行脚本时,必须带路径,例如./run.sh,否则系统会从环境变量中寻找该脚本,导致执行失败

作为解释器参数

1
/bin/bash run.sh

变量

定义变量

变量只能由英文字母、数字和下划线组成,且不能以数字开头

1
output="hello world"	# 变量定义时必须赋初始值

使用变量

通过在变量名前加$符来使用该变量,建议在变量名外加上大括号,以此来区分变量名边界

1
2
echo $username
echo ${username}s		# 通过变量名外的大括号,系统可正常识别变量名边界

字符串

定义字符串

字符串可由单引号或双引号包裹,区别是:单引号中的字符串会原样输出,即变量和转义符无效

1
2
3
name='tom'
str1='hello, $tom \n'	# 单引号中,变量和转义符会原样输出
str2="hello, $tom \n"	# 双引号中,变量和转义符正常输出

字符串拼接

Shell中,拼接字符串无需使用加号(+),直接拼接即可

1
2
3
4
str1="hello"
str2="world"
echo "${str1}, $str2"
echo "$str1, tom"

获取字符串长度

1
2
str="hello, world"
echo ${#str}

提取字符串

1
2
str="abcdef"
echo ${str:3:2} 		# 从索引为3的字符(第一个字符的索引为0)开始,截取2个字符,即输出 de

数组

定义数组

使用圆括号表示数组,数组元素以空格隔开

1
2
fruits=(apple orange pear) 		# 定义数组
fruits[10]="banana"				# 为数组元素赋值,数组下标可不连续,例如此处可不定义fruits[10]之前的元素

获取数组元素

使用数组下标获取数组元素,数组下标从0开始,使用@获取数组中的所有元素

1
2
3
4
echo ${fruits[0]} 				# 获取下标为0的元素,输出 apple
echo ${fruits[10]} 				# 获取下标为10的元素,输出 banana
echo ${fruits[@]} 				# 获取数组所有元素,输出 apple orange pear banana
echo ${#fruits[*]}				# 获取数组元素个数,即数组长度

传递参数

传递参数的shell脚本示例如下(注意:从第10个参数起,后面的参数必须加大括号):

1
2
3
4
5
6
7
#!/bin/bash
echo "shell脚本名:$0"		  # shell脚本名
echo "第一个参数:$1"			# 第一个参数
echo "第二个参数:$2"			# 第二个参数
echo "第十个参数:${10}"		# 第十个参数
echo "传入参数个数:$#"		# 传入参数个数
echo "脚本"

执行sh test.sh args1 args2传入args1和args2,执行结果如下:

1
2
3
4
shell脚本名:test.sh
第一个参数:args1
第二个参数:args2
传入参数个数:2
参数 说明
$0 shell脚本名
$n 执行shell脚本时的第n个入参
$# 入参个数
$$ 脚本执行时的进程ID
$* 以字符串形式显示所有入参
$@ 以“$1” “$2”…“$n”形式显示所有入参

运算符

算数运算符

运算符 说明
+ 加法
- 减法
* 乘法
/ 除法
% 取余
= 赋值
== 等于
!= 不等于

关系运算符

注意:关系运算符仅支持数字

运算符 说明
-eq 判断两个数是否相等
-nq 判断两个数是否不相等
-gt 判断左边的数是否大于右边的数
-lt 判断左边的数是否小于右边的数
-ge 判断左边的数是否大于等于右边的数
-le 判断左边的数是否小于等于右边的数

布尔运算符

运算符 说明
! 非运算
-o 或运算
-a 与运算

逻辑运算符

运算符 说明
&& 逻辑与
|| 逻辑或

字符串运算符

运算符 说明
= 判断字符串是否相等
!= 判断字符串是否不相等
-z 判断字符串长度是否为0
-n 判断字符串长度是否不为0

文件测试运算符

运算符 说明
-b 判断文件是否为块设备文件
-c 判断文件是否为字符设备文件
-d 判断文件是否为目录
-e 判断文件(包括目录)是否存在
-f 判断文件是否为普通文件
-u 判断文件是否设置了SUID位
-g 判断文件是否设置了SGID位
-k 判断文件是否设置了粘着位
-r 判断文件是否可读
-w 判断文件是否可写
-x 判断文件是否可执行
-s 判断文件是否为空

流程控制

判断

1
2
3
4
# if循环
if condition; then
	command1
fi
1
2
3
4
5
6
# if else循环
if condition; then
	command1
else
	command2
fi
1
2
3
4
5
6
7
8
# if else-if else循环
if condition1; then
	command1
elif condition2
	command2
else
	command3
fi

循环

1
2
3
4
5
# for循环
for var in item1 item2 ... itemN
do
	command
done
1
2
3
4
5
# while循环
while condition
do
	command
done

选择

1
2
3
4
5
6
7
8
case in
item1)
	command1
	;;
item2)
	command2
	;;
esac

函数

函数定义格式如下(方括号中的内容可省略):

1
2
3
4
5
[function] funname [()]
{
	command
	[return [int]]
}

示例:

1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
# 无入参的函数
function my_func1()
{
	echo "无参数,无返回值的函数"
}
# 调用函数
my_func1

# 带返回值的函数
# 说明:使用$?获取函数返回值,return后的返回值为可选,取值为0-255,如果不写,则返回值为最后一条命令的执行结果
function my_func2()
{
	echo "有返回值的函数"
	return 100
}
# 调用函数
my_func2

# 有入参的函数
function my_func3()
{
	echo "有入参的函数"
	echo "第一个入参为" $1
	echo "第二个入参为" $2
}
# 调用函数
my_func3 "hello" "world" 100