Linux脚本编程
目录
一、什么是脚本
二、使用方式
三、语法说明
第一个常用命令:echo 回显
shell中特殊符号
重定向
变量
预定义变量(包括环境变量)
test命令
条件判断
循环
while循环
for循环
函数
四、测试练习
shell
终端只是一个界面, 真正在用户和内核之间传递命令和信息的是shell
各种命令, 学的那么多命令行, 本质都是学怎么用这个shell
一、什么是脚本
预先设定好的一连串命令, 让shell执行就是脚本
类似: windows下批处理, photoshop 的动作, 按键精灵等
二、使用方式
- 创建脚本文件, 一般使用
.sh
后缀, 格式为, 如shell.sh
#!/bin/bash
echo "脚本开始"
ls -al /etc
echo "脚本结束"
-
#!/bin/bash作用是告诉操作系统使用
/bin/bash
来执行该脚本。 -
添加执行权限
chmod +x shell.sh
-
使用
./<filename>
直接执行, 或者bash <filename.sh>
执行
必须
./<filename>
, 不能filename
, 原因与#PATH有关需要可执行权限, 是因为
./shell.sh
相当于将脚本文件作为可执行程序来运行, 所以需要x
权限
三、语法说明
-
第一个常用命令:
echo
回显-
即将后面的内容显示出来
-
-e
选项表示支持转义模式, 可以显示\n
换行\t
制表符等 -
如
echo 123
和echo abc
等, 就会直接在屏幕上显示123 abc -
echo "内容" >> file
将内容写到文件内
-
-
-
shell中特殊符号
-
以
#
开头的是注释内容, 不生效 -
~
为用户主目录 -
*
任意匹配字符 ,?
任意匹配单个字符,[]
匹配方括号内的单个字符 -
$
为取值 -
> >> < << 2> 2>>
重定向-
>
和>>
为重定向标准输出stdout
, 即将正确的输出内容转到文件内 -
2>
和2>>
为重定向标准错误输出stderr
, 即将错误的输出内容转到文件内 -
<
为重定向标准输入stdin
, 即从文件内输入原本由屏幕输入的内容
-
-
|
管道 即将|符号前一个命令输出的结果作为|符号后一个命令的输入
, 管道可以连续嵌套
-
-
重定向
-
输出内容(注意是内容不是结果
$?
)可能是正确输出, 也可能是有问题的输出, 前者用> >>
重定向,后者用2> 2>>
重定向, 如whereis ls > findresult 2> notfindresult
.-
若要正确和错误内容都输入同一个文件, 用
[某语句] > result 2>&1
-
-
# 示例, 一个命令同时会有正确结果和错误结果时, 将结果全重定向到一个文件内
touch file1 file2 file3 # 创建三个文件
sudo chown root:root file3 # 将其中一个文件权限修改, 使得tar无法打包
sudo chmod 700 file3
tar -czvf ./tartest.gz.tar ./file1 ./file2 ./file3 > ./tar.log 2>&1
cat tar.log
# tar打包过程中, 每成功打包一个文件会输出一条正确输出, 每不成功打包一个文件会输出一条错误输出
# 前述命令将正确输出的内容输出到tar.log内(> tar.log) 错误输出也输出到这个文件( 2>&1 )
-
/dev/null
可作为不需要的内容的重定向结果, 比如不想要看到错误, 或者完全不想看过程 -
输入内容(原本用键盘的)可以改用
<
从其他文件读取, 比如sudo ls < passwordfile
-
变量
-
定义和赋值用
var=aa
, 取值用$var
或者${var}
-
变量名必须是字母或者数字, 但是不能以数字开头, 局部变量用小写, 系统变量为大写
-
${val}
可以取变量的值 -
$(cmd)
取命令的结果值 -
变量默认是字符串
$((num1+num2))
取数字计算值 -
${var}
写在双引号内会正常取值, 写在单引号内则会使用字面符号, 以var变量为例-
echo "var = ${var}"
会输出var = aa
-
echo 'var = ${var}'
会输出var = ${var}
-
-
定义和赋值的只在本次脚本内有效
-
-
-
预定义变量(包括环境变量)
-
本质也是一种变量, 只不过由系统提前定义好的, 全局有效的变量, 一般用大写
-
$PATH
, 常用命令所在的目录集合 -
$SHELL
, 当前的环境的shell -
$HOME
当前用户的主目录 -
$USER
当前用户名 -
$PWD
当前路径 -
$?
表示前一条命令执行的结果, 0为成功, 其他为不成功 -
$0
脚本名,$1~n
第一到第n个参数,,$#
参数个数,$@
表示所有参数
-
# 命令
./test.sh aa bb cc
# 得到的参数
echo $0 # 结果为./test.sh
echo $1 # 结果为aa
echo $2 # 结果为bb
echo $3 # 结果为cc
echo $# # 结果为3,即有三个参数
echo $@ # 结果为aa bb cc, 即所有参数
-
test命令
-
判断一个表达式是否为真, 从输出的
$?
可以判断结果-
test -f path
文件是否存在,-d
目录是否存在,-e
文件或目录是否存在 -
test n1 -eq n2
数字n1是否等于数字n2,-lt
小于-gt
大于-
eq
: equalgt
:greater thanlt
: lesser thange
greater or equalle
lesser or equal
-
-
test -n string
真表示string不为空, 一般用于判断是否定义了变量-
必须使用类似
test -n "$var"
这种形式, 使用双引号将变量指明为字符串
-
-
test string1 == string2
判断两个字符串相等,!=
表示不等-
string1和string2可以是直接的字符串也可以是变量 , 为了安全, 应该都加双引号
-
-
test
命令前加!
表示测试条件取反 如! test 5 -le 3
-
test命令常简写为方括号
[ -f path ]
的形式, 方括号与其他 同样支持!
取反 -
test中字符变量最好都用双引号, 如
[ "${a}" == "${b}" ]
-
-
条件判断
if 条件1 ; then
语句1
语句2
elif 条件2 ; then
语句3
语句4
else
语句5
fi
循环
while循环
// 参考C语言的写法
int nu = 1;
while(nu < 5)
{
printf("%d", nu);
nu = nu + 1;
}
# shell脚本中的写法
nu=1
while test nu -le 5
do
echo "number is ${nu}"
nu=$((${nu}+1))
done
for循环
#!/bin/bash
read -p "输入重复次数:" n
for (( i=0; i<=${n}; i++ ))
do
echo i
done
for var in string1 string2 string3
do
echo $var
done
实现将/etc/passwd目录下的用户打印出来
#!/bin/bash
users=$(cut -d ":" -f 1 /etc/passwd)
for user in $users
do
echo "user name = ${user}"
done
函数
# 函数定义
function 函数名() {
#return #直接返回函数, 则下一行的echo不会执行
echo "123"
}
# 函数使用
函数名
四、测试练习
-
循环ping 192.168.31网段的所有主机
#!/bin/bash
i=1
for i in {1..254}
do
ping -c 2 -w 3 -i 0.3 192.168.31.$i $> /dev/null
if [ $? -eq 0 ] ;then
echo "192.168.31.$i is yes"
else
echo "192.168.31.$i is no"
fi
i=$((${i}+1))
done
-
猜数字游戏
while :
do
read -p "计算机生成了一个 1‐100 的随机数,你猜: " cai
if [ $cai -eq $num ]
then
echo "恭喜,猜对了"
exit
elif [ $cai -gt $num ]
then
echo "Oops,猜大了"
else
echo "Oops,猜小了"
fi
done
- 阶乘
#!/bin/bash
read -p "请输入你想要的阶乘" p
jiecheng=1
for ((i=1;i<=$p;i++))
do
jiecheng=$[jiecheng*i]
done
echo $jiecheng