shell编程入门指南
---大头针
一、变量
变量:C也是 从变量开始学起。shell编程也从变量学起。
变量三个方面:1、数据类型 2、生存期 3、作用域
1.1 数据类型:变量依据你赋值的类型
C与Shell对比:
C:
int a="abcd";(错误)
Shell:
a="abcdef"
a就是字符串类型
b=3
b就是整型
1.2 变量
从变量的生存期和作用域角度划分一般使用到得变量有三种。
1.本地变量
在用户现在的shell生命期的脚本中使用,如果shell启动另一个进程或退出,此值失效。
有5种常用的使用方法:
1.变量赋值
a="abcd"
2.显示变量
echo $a
3.清除变量
unset a
4.显示所有本地shell
set
5.只读变量
name="abc"; readonly name
2.环境变量
登录进程为父进程,shell中执行的用户进程为子进程。环境变量可用于所有子进程。环境变量最好在profile文件中定义。习惯上,所有环境变量均应该大写。
有5种常用的使用方法:
1.变量赋值
abc="abc";export abc
2.显示环境变量
echo $abc
3.显示所有环境变量
env
4.清除环境变量
unset abc
5.常用环境变量
HOME PATH PWD USER
3.位置变量
这个特别适合于执行命令时,传递参数。
1.位置变量一般用$0--$9
例如:
service httpd start
$0表示:service
$1表示:httpd
$2表示:start
2.$#表示参数的总个数
使用变量时注意事项:
在使用C编程的时候,在使用变量时,如果变量没有被赋值就使用则会出现问题。Shell有专门的检测变量是否被设置的方法:
测试变量是否已经设置
1.${var:-value}:
如果变量var未定义,返回一个默认值如果var存在且非空,则表达式${var:-value}的值为$var,如果var未定义,则表达式值${var:-value}为value.
name1="dong";name2=${name1:-no name};echo $name1 $name2
unset name1; name2=${name1:-no name};echo $name1 $name2
2.${var:=value}:
如果var未定义,设置var的默认值为value
如果var存在且非空,则${var:=value}的值为$var;如果var为空或未定义,则var被赋值value且表达式值为value。
3.${var:?mesg}
捕获未定义变量导致的错误。
如果var存在且非空,则${var:?value}的值为$var;如果var为空或未定义,则打印mesg并终止脚本。
4.${var:+mesg}:
测试一个变量的存在性
如果var存在且非空,则${var:+mesg}的返回值为mesg;如果var为空或未定义,则返回null
二、条件:
对于我们写程序来说,无论选择结构和循环结构都离不开条件。C语言的条件主要由运算符组成的各类表达式组成,条件的组成非常灵活。而shell的条件一般分为三类。其中的文件状态条件都是系统设置好的,只有记住才能够利用好。
2.1.文件状态的条件
1. file1 -ef file2 file1和file2有相同的设备和相同节点号。
2. file1 -nt file2 file1比file2修改时间更晚。
3.file1 -ot file2 file1比file2修改时间更早
4. -b file1 file1存在并且是块设备
5. -c file1 file1存在并且是字符设备
6. -d file1 file1存在并且是目录
7. -e file1 file1存在
8. -f file1 file1存在并且是普通文件
9. -g file1 file1存在并且有组ID
10. -h file1 file1存在并且是软链接文件
-L file1
11. -G file1 file1存在并且拥有者所在的组也存在
12. -k file1 file1存在并且粘滞位已设置
13. -O file1 file1存在并且拥有者也存在
14. -p file1 file1存在并且是管道文件
15. -s file1 file1存在并且是非空文件
16. -S file1 file1存在并且是进程
17. -t file1
18. -u file1 file1存在并拥有者的ID位已设置。
19. -w file1 file1存在并可写
20. -x file1 file1存在并可执行
2.2.字符串的条件
C语言中字符串的比较是通过strcmp(str1,str2) 用函数实现字符串比较
而Shell则比较简单:
1. -z string:字符串为空串时返回真
2. -n string: 不为空串
3. str1 = str2 : 相等
4. str1 != str2: 不相等时返回真
5. str1
6. str1>str2:
2.3.有关数值的条件
C语言中数值比较,是通过算术运算符(> < =等)实现,而shell利用了一些单词缩写实现。
int1 -eq int2 等于
-ne 不等于
-lt 小于
-le 小于等于
-gt 大于
-ge 大于等于
三、控制结构:
C的程序结构与Shell的程序结构大同小异。
3.1选择结构:
1.If结构
if [ conditon1 ]
then
statments1
elif [ condition2 ]
then
statments2
else
statments3
fi
2.case结构
case variable in
value) command1
exit 0
;;
value) command 2
exit 0
;;
esac
3.2.循环结构:
1.for结构
for name [in list]
do
statements using $name
done
1.list应该是一系列由空格分隔的字符序列(单词),省略in list 时默认为
$@(命令行的参数列表)
2.for循环执行的次数取决于列表list中单词的个数
3.在for循环体中一般要出现变量$name,但也可以不出现。
2.循环结构:until
until [ condition ]
do
statments
done
condition 条件成立退出循环
3.循环结构:while循环
while [ condition ]
do
statments
done
条件不成立退出循环
备注:
还有一些经常与循环结合的命令:比如break [n]、continue [n]。和C中break Continue功能基本一致。只不过break可以选择跳出几层循环、continue可以选择跳过几个回合。
四、命令
熟悉了上面三部分内容对于我们写shell程序奠定了基础。但巧妇难为无米之炊
。shell程序的主体内容是shell所提供的命令:例如 cp ls useradd。
如果你没有系统学习过shell的命令,你是写不出来shell程序的。
最后得出结论:
变量+条件+程序结构+shell命令==shell程序。
五、实例:
1. 编写shell程序,实现自动增加50个账号的功能。账号名为stud1至stud50。
#! /bin/bash
#useradd.sh
#i这属于 变量
i=1
#while 这属于 程序结构
while [ $i -le 50 ]
do
#cat ...命令的含义是使用管道以及正则表达式查看passwd文件中是否存在类似#stud1-stud50之间的用户. 这属于 shell 命令
# -z 测试字符串是否为空.这属于 条件
if [ -z "`cat /etc/passwd|grep "stud$i/>"`" ]
then
useradd stud$i
echo "useradd success!"
else
"user stud$i exist!"
fi
done
最终验证了我的结论:
shell程序=变量+条件+程序结构+shell命令。
一开始接触linux shell,大多都认为比较难学。但按照上面的学习思路,很快你就会学会shell编程。
六、补充知识:
函数:
Shell也提供了函数机制。格式如下:[function] NAME() {command-list;}
返回值:return [n]
将函数的返回值设定为n .若不指定n值,则使用return 之前所执行的最后一个命令的状态值。
$?
执行后命令后的状态
实例:
#!/bin/bash
function psgrep
{
ps –aux|grep $1
}