shell脚本的运行方法
-
直接指令下达 shell.sh文件比较具备可读和可执行权限(rx),有以下3种方式执行:
绝对路径:/home/user/shell.sh
相对路径:./shell.sh
变量PATH功能:将shell.sh放在PATH指定目录内如 ~/bin -
以bash程序来执行:通过
bash shell.sh
或sh shell.sh
shell脚本的参数
在执行shell脚本时,可以在脚本名后面加入参数,$0表示脚本名,$1表示第一个参数,$2表示第二个…如:
/path/to/scriptname opt1 opt2 opt3 opt4
$0 $1 $2 $3 $4
参数表示 | 意义 |
---|---|
$0 | 脚本名本身 |
$1,$2,$3… | 脚本的第一,二,三个参数… |
$# | 表示参数的个数 |
$@ | 列出所有参数,所有参数之间彼此独立 |
$* | 列出所有参数,这些参数会被看作是一个整体 |
#! /bin/bash
echo "shows the script name, parameters."
echo "This script name is: " ${0}
echo "Total parameters number is: " $#
echo "show all parameters" "$@"
echo "first param is: " ${1}
echo "second param is: " ${2}
执行param.sh a b c d
shows the script name, parameters.
This script name is: param.sh
Total parameters number is: 4
show all parameters a b c d
first param is: a
second param is: b
关于$@和$*的区别使用echo输出是看不出两者有什么不同,但可以使用for…in…循环可以看出不同:
下面代码保存为test.sh
#! /bin/bash
echo 'show what diffent between $@&$*'
echo '$@'
for i in "$@"
do
echo ${i}
done
echo
echo '$*'
for i in "$*"
do
echo ${i}
done
执行test.sh 1 2 3 4 输出结果:
show what diffent between $@&$*
$@
1
2
3
4
$*
1 2 3 4
对于$@循环输出了4次,说明参数是独立的,$*只循环输出了1行,说明这些参数是一个整体。
if…then…fi
if [ 条件判断式1 ]; then
当判断式1成立时,可以执行的指令
elif [ 条件判断式2 ]; then
当判断式2成立时,可以执行的指令
elif [ 条件判断式3 ]; then
当判断式3成立时,可以执行的指令
......
else
上面都不成立时,可以执行的语句
fi
例:输入一个分数成绩,对成绩进行判断为‘优(80-100)’、‘良(60-79)’、‘不合格(0-59)’。
#! /bin/bash
read -p "please input a number: " number
expr $number + 0 &> /dev/null # 通过expr的返回值验证输入的内容是否为整数
if [ "$?" -le 1 ]; then # expr的返回值不大于1,那么number就是一个整数
if [ "$number" -ge 0 ] && [ "$number" -le 100 ]; then
if [ "$number" -ge 80 ]; then
echo "优"
elif [ "$number" -ge 60 ]; then
echo "良"
else
echo "不合格"
fi
else
echo "not in 0-100" && exit 0
fi
else
echo "not a number" && exit 0
fi
case…in…esac
当判断条件内容为多个的时候可以使用case进行判断
case $变量 in
模式1)
命令1
;;
模式2)
命令2
;;
模式3)
命令3
;;
......
*) # 代表其他所有情形,同else
默认执行命令
esac
例:输入一个字符判断式字母字符还是标点符号
#! /bin/bash
read -p "plsase input a word: " word
case $word in
[0-9])
echo "number"
;;
[a-zA-Z])
echo "letter"
;;
[[:punct:]])
echo "punct"
;;
*)
echo "Error, please input one letter or one number or one punct"
esac
shell函数
用户可以自定义函数,函数需要在脚本的开始时声明,然后就可以在脚本中随意使用。函数可以function fun()
定义,也可以直接fun()
直接定义,不带任何参数。函数还可以使用return
返回一个整数(0-255)的值,不使用return那么函数的最后一条命令就是返回值。
[function] fun(){
action
}
调用函数时可以为函数添加参数,下面表格中,前5项都必须在函数体内
使用
调用符号 | 意义 |
---|---|
$0 | 表示函数自身 |
${1},${2},${3}… | 第一、第二、第三…个函数的参数 |
$# | 传递到函数的参数个数 |
$@ | 展示所有函数的参数,这些参数相互独立 |
$* | 展示所有函数的参数,这些参数为一个整体 |
$? | 在脚本内使用时,$?表示调用函数的返回值 |
例:func.sh接收并判断前2个参数是否为整数,然后2个参数相加并输出结果
#! /bin/bash
function func(){
expr ${1} + 0 &> /dev/null
if [ $? -le 1 ] && [ $1 != " " ]; then
expr ${2} + 0 &> /dev/null
if [ $? -le 1 ] && [ $2 != " " ]; then
echo "the first parameter is ${1}"
echo "the second parameter is ${2}"
return $((${1}+${2}))
else
echo "make sure the second parameter is a number"
fi
else
echo "make sure the first parameter is a number"
fi
}
func ${1} ${2}
echo "total is $?"
func 10 11
echo "total is $?"
执行脚本
./func.sh 4 5
the first parameter is 4
the second parameter is 5
total is 9
the first parameter is 10
the second parameter is 11
total is 21
这个程序里面调用了2次func这个函数,第一次调用时,函数的参数是func.sh的参数是4和5,在脚本里面函数func直接调用脚本的参数1和参数2作为自己的参数,然后$?调用返回的值。第二次调用时直接给与10和11这2个参数进行计算。
while…do…done和until…do…done
while循环,当满足条件时,循环继续,当不满足条件时,退出循环
until循环,当不满足条件时,循环继续,当满足条件时,退出循环
当while没有条件时,需在while后面加:
while|until [判断条件]
do
action
done
例:从1加到100,输出结果
#! /bin/bash
i=1
sum=0
while [ "${i}" -le 100 ]
do
let sum=sum+i
let i++
done
echo "total is $sum"
例:利用死循环,让用户选择选项
#! /bin/bash
while :
do
echo "**********************"
echo "1. time and date"
echo "2. system info"
echo "3. users are doing"
echo "4. exit"
echo "**********************"
read -p "enter you chioce [1-4]: " choice
case $choice in
1)
date
read -p "press any key to continue..."
;;
2)
uname -r
read -p "press any key to continue..."
;;
3)
w
read -p "press any key to continue..."
;;
4)
echo "byebye!"
exit 0
;;
*)
echo "you must choice [1-4]"
;;
esac
done
例:输入一个数字,程序会从1加到输入的数字并输出结果
#! /bin/bash
while :
do
read -p "please input a number: " number
expr ${number} + 0 &> /dev/null
if [ $? -le 1 ]; then
i=0
sum=0
while [ ${i} -le ${number} ]
do
let sum=sum+i
let i++
done
echo "total is ${sum}" && exit 0
fi
done
for…in…
for循环将会循环n次,并输出n个结果
for var in list
do
action
done
例:将一个数组的内容都输出后加上2
#! /bin/bash
list=(1 2 3 4)
for i in ${list[@]} # ${list[@]}表示完整一个数组
do
let j=i+2
echo ${j}
done
# 输出
3
4
5
6
另一种写法for((初始值;限制条件;执行操作))
list=(1 2 3 4)
for((i=0;i<${#list[@]};i++)) # ${#list[@]}表示这个数组的个数
do
let j=i+2
echo${j}
done
练习:先查看一下 /home/python/test/logical 这个名称是否存在; 若不存在,则创建一个文件,使用touch 来创建,创建完成后离开; 如果存在的话,判断该名称是否为文件,若为文件则将之删除后创建一个目录,文件名为 logical ,之后离开; 如果存在的话,而且该名称为目录,则移除此目录。
#! /bin/bash
pathname="/home/python/test/logical"
if [ ! -e "${pathname}" ]; then
echo "不存在文件${pathname}" && mkdir ~/test &> /dev/null; echo "新创建文件${pathname}" && touch ~/test/logical && echo "文件创建成功" && exit 0
else
if [ -f "${pathname}" ]; then
echo "${pathname}是一个文件并将其删除" && rm -rf ~/test/logical && echo "成功删除文件并创建新目录${pathname}" && mkdir ~/test/logical/ && echo "成功创建目录" && exit 0
elif [ -d "${pathname}" ]; then
echo "${pathname}是一个目录并将其删除" && rm -rf ~/test/logical/ && echo "成功删除目录"
fi
fi