脚本简单地说就是一条条的文字命令,这些文字命令是可以看到的(如可以用记事本打开查看、编辑),脚本程序在执行时,是由系统的一个解释器,将其一条条的翻译成机器可识别的指令,并按程序顺序执行。因为脚本在执行时多了一道翻译的过程,所以它比二进制程序执行效率要稍低一些。 
 
   脚本可以自动化完成某个工作,所以说写好脚本可以使运维工程师的工作更加轻松。
 
    shell script是利用shell的功能所写的一个“程序”(program),这个程序是使用纯文本文件,将一些shell的语法或命令写在里面,搭配正则表达式、管道命令与数据流重定向等功能,以达到我们所想要的处理目的。
 
学习shell script的好处:
    1、自动化管理(比如说把每天都需要手动执行的任务写成一个脚本,让其在指定的时间内运行)
    2、追踪与管理系统 (比如说启动Linux 服务)
    3、简单的***检测功能 (比如说可以写一个脚本,让其自动检测系统有没有异常,如果有异常,就通知管理员或立即加强防火墙规则)
    4、连续命令单一化 (是指整合一些在命令行执行的连续命令,将它们写在脚本中,而后直接执行脚本就OK了)
    5、简易的数据处理 (比如说比较两个数据的比较、字符串是否相等)
    6、跨平台
    7、可以帮助我们弄清楚Linux的来龙去脉 
 
 
下面就开始脚本编程的基础知识学习吧 !
 
一、善于使用判断式:
    test命令和判断符号[]都可以用于测试字符串、文件状态和数字,也可以同控制流结合。
   
语法格式:
    test 条件判断式
    [ 条件判断式 ]   注意:中括号和条件判断式之间必须要有空格
 
1、字符串测试:
=(或==) 两个字符串是否相等
!= 两个字符串是否不相等
-z 判断字符串是否为空,若为空则为真
-n 判断字符串是否为不空,若为不空则为真
2、文件类型判断:
-e 该文件名是否存在
-f 该文件名是否存在并且为文件
-d 该文件名是否存在并且为目录
-L 该文件名是否存在并且为链接文件
-b 该文件名是否存在并且为块设备
-c 该文件名是否存在并且为字符设备
-p 该文件名是否存在并且为管道文件
-s 该文件名是否存在并且为套接字文件
 
3、文件权限检测:
-r 该文件名是否存在并且具有可读权限
-w 该文件名是否存在并且具有可写权限
-x 该文件名是否存在并且具有可执行权限
-u 该文件名是否存在并且具有SUID属性
-g 该文件名是否存在并且具有SGID属性
-k 该文件名是否存在并且具有Sticky属性
-s 该文件名是否存在并且为非空白文件
 
4、数值测试:
-eq 两个数值相等(equal)
-ne 两个数值不等(not equal)
-gt 数值1大于数值2(greater than)
-lt 数值1小于数值2(less than)
-ge 数值1大于等于数值2(greater than or equal)
-le 数值1小于等于数值2(less than or equal)
 
5、多重条件判断:
-a,&& 逻辑与
-o,|| 逻辑或
 
 
二、条件判断式用法详解:
 
1、if条件判断
   if条件判断是指当符合某个条件时就执行。
 
单分支if语句:
单分支的if语句是最简单的选择结构,这种结构只判断指定的条件,当“条件成立”时执行相应的操作。否则不做任何操作,语句格式如下:
if [条件判断式];then
statement 
fi
 
例子:
   写一个脚本,使用if语句计算2个数的大小,如果数字2大于数字1,就显示数字2>数字1 。
 
脚本内容如下:
 
  
  1. #!/bin/bash 
  2. #Name:compare 
  3. #Description:compare the size of two numbers 
  4. #Author:Linli 
  5. #Version:0.0.1 
  6. #Datatime:06/16/12 14:15:00 
  7. #Usage: ./compare.sh NUM1 NUM2 
  8.  
  9. ##### scripts ######## 
  10. if [ $1 -le $2 ];then 
  11.         echo "$2 > $1" 
  12. fi 
  13. ##### scripts ######## 
脚本执行结果如下:
 
  
  1. [root@www.magedu.com scripts]# ./compare.sh 2 3 
  2. > 2 
 
双分支if语句:
双分支的if语句使用了两路命令操作。在条件成立或不成立的时候分别执行不同的命令序列,,格式如下:
if [条件判断式];then
statement
else
statement
fi
 
例子:
   补充上面的脚本,如果数字2不大于数字1,就显示数字2<=数字1。
   将上面脚本中的scripts中的内容修改为如下内容:
 
  
  1. ##### scripts ######## 
  2. if [ $1 -le $2 ];then 
  3.         echo "$2 > $1" 
  4. else 
  5.     echo "$2 <= $1" 
  6. fi 
  7. ##### scripts ######## 
脚本执行结果如下:
 
  
  1. [root@www.magedu.com scripts]# ./compare.sh 3 1  
  2. <= 3 
 
 
 
多分支if语句:
多分支if语句,可以进行多次判断,格式如下
 
if [条件判断式];then
statement 1
elif [条件判断式];then
statement 2
elif [条件判断式];then
...
else
statement n
fi
 
例子:
   补充上面的脚本,如果数字2小于数字1,就显示数字2<数字1,否则就显示数字2=数字1。
   将上面脚本中的scripts中的内容修改为如下内容:
 
  
  1. ##### scripts ######## 
  2. if [ $1 -lt $2 ];then 
  3.         echo "$2 > $1" 
  4. elif [$1 -gt $2 ] 
  5.     echo "$2 < $1" 
  6. else 
  7.     echo "$2 = $1" 
  8. fi 
  9. ##### scripts ######## 
脚本执行结果如下:
 
  
  1. [root@www.magedu.com scripts]# ./compare.sh 3 1  
  2. < 3 
  3. [root@www.magedu.com scripts]# ./compare.sh 3 3  
  4. 33 = 3 
 
 
 
2、case...esac
  常用于一个变量可能有多个变量值,每一个变量值执行不同的代码段。
使用格式:
case $变量名称 in
变量值1)
  statement
  ;;
变量值2)
  statement
  ;;
...
*)
  statement
  ;;
esac
 
例子:
   写一个脚本,使用case语句完成以下功能:
 
   1、提示用户输入一个用户名;
   2、显示一个菜单给用户,形如:
   
     U|u  show UID
     
     G|g  show GID
   
     S|s  show SHELL
   
     Q|q  quit 。
   3、提醒用户选择一个选项,并显示其所选择的内容;
 
脚本内容如下:
 
  
  1. #!/bin/bash 
  2. #Name:menu 
  3. #Description:case 
  4. #Author:Linli 
  5. #Version:0.0.1 
  6. #Datatime:06/17/12 15:00:00 
  7. #Usage: ./menu.sh  
  8.  
  9. ##### scripts ######## 
  10. read -p "Please key in an user name: " name 
  11.  
  12. cat << EOF 
  13. U|u)  show UID 
  14. G|g)  show GID 
  15. S|s)  show SHELL 
  16. Q|q)  quit 
  17. EOF 
  18.  
  19. read -p "Please key in  your choice: " choice 
  20. case $choice in 
  21.   U|u) 
  22.     id -u $name 
  23.     ;; 
  24.   G|g) 
  25.     id -g $name 
  26.     ;; 
  27.   S|s) 
  28.     grep "^$name" /etc/passwd | cut -d: -f7 
  29.     ;; 
  30.   Q|q) 
  31.     echo "quit" 
  32.     exit 0 
  33.     ;; 
  34. esac 
  35. ##### scripts ######## 
脚本执行结果如下:
 
  
  1. [root@www.magedu.com scripts]# ./menu.sh 
  2. Please key in an user name: bin 
  3. U|u)  show UID 
  4. G|g)  show GID 
  5. S|s)  show SHELL 
  6. Q|q)  quit 
  7. Please key in  your choice: u 
 
 
3、脚本function
shell script中的函数就是自定义一段执行代码,也可以说成是一些功能模块,有利于结构化编程和代码重用。
脚本function的使用格式:
function 函数名 {
  statement
}
 
函数名() {
  statement
}
 
 
例子:
   写一个脚本:
   使用函数实现:
   
   1、判断一个用户是否存在,用户名通过参数传递而来;
 
      如果存在,就显示此用户的shell和UID
 
      如果不存在,就说此用户不存在;
   
   2、提示用户输入用户名,而后将其传递给上面的函数;
   
   3、判断结束后不退出,而是提示用户可继续输入其它用户名,或输入(quit)退出;
 
脚本内容如下:
 
  
  1. #!/bin/bash 
  2. #Name:user 
  3. #Description:function 
  4. #Author:Linli 
  5. #Version:0.0.1 
  6. #Datatime:06/17/12 15:40:00 
  7. #Usage: ./user.sh  
  8.  
  9. ##### scripts ######## 
  10. myuser() { 
  11.   if `grep "$1" /etc/passwd &> /dev/null` ;then 
  12.     echo "shell: `grep "^$1" /etc/passwd | cut -d: -f7`  UID:`id -u $1`" 
  13.   else 
  14.     echo "This user is not exist..." 
  15.   fi 
  16.  
  17. read -p "Please key in an user name:  " name 
  18. until [ "$name" == "quit" ];do 
  19.   myuser $name 
  20.   read -p "You can continue key in an user name:  " name 
  21. done 
  22. echo "quit" 
  23. ##### scripts ######## 
脚本执行结果如下:
 
  
  1. [root@www.magedu.com scripts]# ./user.sh  
  2. Please key in an user name:  root 
  3. shell: /bin/bash  UID:0 
  4. You can continue key in an user name:  bin 
  5. shell: /sbin/nologin  UID:1 
  6. You can continue key in an user name:  gentoo 
  7. shell: /bin/bash  UID:502 
  8. You can continue key in an user name:  quit 
  9. quit 
  10. [root@www.magedu.com scripts]# 
 
注意:
    函数的返回值是函数调用时所执行的函数体中的最后一条语句的状态返回值;可以使用return命令自定义函数返回值。
 
三、循环
   循环分为不定循环和固定循环(即循环几次是事先定义好的)
 
1、不定循环
  不定循环是指符合指定的条件就循环执行某段代码段。
  不定循环有:while..do..done 、 until..do..done
  使用格式为:
      while [ 条件判断式 ];do
statement
      done
 
      until [ 条件判断式 ];do
statement
      done
 
注意:while是指符合条件判断时才开始循环,直到条件不满足时退出。
      until是指不符合条件判断时才开始循环,直到条件满足时退出。
 
例子1:
   写一个脚本:计算100以内整数的和
 
脚本内容如下:
 
  
  1. #!/bin/bash 
  2. #Name:sum 
  3. #Description:while 
  4. #Author:Linli 
  5. #Version:0.0.1 
  6. #Datatime:06/17/12 16:10:00 
  7. #Usage: ./sum.sh  
  8.  
  9. ##### scripts ######## 
  10. declare -i sum=0 
  11. declare -i I=1 
  12.  
  13. while [ $I -le 100 ];do 
  14.   sum+=$I 
  15.   let I++ 
  16. done 
  17. echo "1+2+3+..+100=$sum" 
  18. ##### scripts ######## 
脚本执行结果如下:
 
  
  1. [root@www.magedu.com scripts]# ./sum.sh 
  2. 1+2+3+..+100=5050 
 
 
例子2:
  写一个脚本,显示此分区使用率的相关信息:
 
    1、提醒用户输入一个分区,而后显示其使用率信息;
    2、直到用户输入q或Q退出;
 
脚本内容如下:
 
 
  
  1. #!/bin/bash 
  2. #Name:disk 
  3. #Description:until 
  4. #Author:Linli 
  5. #Version:0.0.1 
  6. #Datatime:06/17/12 16:55:00 
  7. #Usage: ./disk.sh  
  8.  
  9. ##### scripts ######## 
  10. read -p "Please key in a disk partition: " disk 
  11. until [ "$disk" == "q" -o "$disk" == "Q" ];do 
  12.   fdisk -l $disk 
  13. done 
  14. echo "quit" 
  15. ##### scripts ######## 
脚本执行结果如下:
 
 
  
  1. [root@www.magedu.com scripts]# ./disk.sh  
  2. Please key in a disk partition: /dev/sda 
  3.  
  4. Disk /dev/sda: 343.5 GB, 343597383680 bytes 
  5. 255 heads, 63 sectors/track, 41773 cylinders 
  6. Units = cylinders of 16065 * 512 = 8225280 bytes 
  7.  
  8.    Device Boot      Start         End      Blocks   Id  System 
  9. /dev/sda1   *           1          13      104391   83  Linux 
  10. /dev/sda2              14        5235    41945715   8e  Linux LVM 
  11. /dev/sda3            5236        5366     1052257+  82  Linux swap / Solaris 
  12. /dev/sda4            5367       41773   292439227+   5  Extended 
  13. /dev/sda5            5367        5975     4891761   fd  Linux raid autodetect 
  14. /dev/sda6            5976        6584     4891761   fd  Linux raid autodetect 
  15. /dev/sda7            6585        7193     4891761   fd  Linux raid autodetect 
  16. /dev/sda8            7194        7802     4891761   fd  Linux raid autodetect 
  17. /dev/sda9            7803        9019     9775521   8e  Linux LVM 
  18. /dev/sda10           9020       10236     9775521   8e  Linux LVM 
  19. /dev/sda11          10237       10480     1959898+  83  Linux 
  20. Please key in a disk partition: q 
  21. quit 
 
补充while的相关知识点:
while true;do
  statement
done
 
while [1];do    这个和while true一样
  statement
done       
 
while read LINE;do
  statement
done < 文件路径
 
下面来举例说明以上3种while循环的使用方法:
例子1:
   写一个脚本,使用while true;do..done 完成以下功能:
 
1、提示用户输入一个用户名;
        2、显示一个菜单给用户,形如:
   
           U|u  show UID
   
           G|g  show GID
   
           S|s  show SHELL
   
           Q|q  quit 。
3、提醒用户选择一个选项,并显示其所选择的内容;显示完成后不退出,继续提示用户输入选项。
 
脚本内容如下:
 
  
  1. #!/bin/bash 
  2. #Name:menu 
  3. #Description:case 
  4. #Author:Linli 
  5. #Version:0.0.1 
  6. #Datatime:06/17/12 17:30:00 
  7. #Usage: ./menu.sh  
  8.  
  9. ##### scripts ######## 
  10. read -p "Please key in an user name: " name 
  11.  
  12. cat << EOF 
  13. U|u)  show UID 
  14. G|g)  show GID 
  15. S|s)  show SHELL 
  16. Q|q)  quit 
  17. EOF 
  18.  
  19. while true;do 
  20. read -p "Please key in  your choice: " choice 
  21.   case $choice in 
  22.     U|u) 
  23.       id -u $name 
  24.       ;; 
  25.     G|g) 
  26.       id -g $name 
  27.       ;; 
  28.     S|s) 
  29.       grep "^$name" /etc/passwd | cut -d: -f7 
  30.       ;; 
  31.     Q|q) 
  32.       echo "quit" 
  33.       exit 0 
  34.       ;; 
  35.     ?) 
  36.       echo "Wrong choice"   
  37.       continue 
  38.       ;; 
  39.   esac 
  40. done 
  41. ##### scripts ######## 
脚本执行结果如下:
 
  
  1. [root@www.magedu.com scripts]# ./menu.sh 
  2. bash menu2.sh 
  3. Please key in an user name: root 
  4. U|u)  show UID 
  5. G|g)  show GID 
  6. S|s)  show SHELL 
  7. Q|q)  quit 
  8. Please key in  your choice: u 
  9. Please key in  your choice: t 
  10. Wrong choice 
  11. Please key in  your choice: s 
  12. /bin/bash 
  13. Please key in  your choice: g 
  14. Please key in  your choice: q 
  15. quit 
 
 
例子2:
 写一个脚本,使用while read LINE;do..done 完成以下功能:
显示/etc/passwd中的每一行内容。
 
脚本内容如下:
 
  
  1. #!/bin/bash 
  2. #Name:read 
  3. #Description:while read LINE 
  4. #Author:Linli 
  5. #Version:0.0.1 
  6. #Datatime:06/17/12 17:30:00 
  7. #Usage: ./read.sh  
  8.   
  9. ##### scripts ######## 
  10. while read LINE;do 
  11.   echo "$LINE" 
  12. echo "OK"
  13. done < /etc/passwd 
  14. ##### scripts ######## 
 脚本执行结果如下:
 
   
  1. [root@www.magedu.com scripts]# ./line.sh 
  2. root:x:0:0:root:/root:/bin/bash 
  3. OK 
  4. bin:x:1:1:bin:/bin:/sbin/nologin 
  5. OK 
  6. daemon:x:2:2:daemon:/sbin:/sbin/nologin 
  7. OK 
  8. adm:x:3:4:adm:/var/adm:/sbin/nologin 
  9. OK 
  10. ... [显示的其它内容省略了]
     
 
 
 
2、固定循环
   固定循环是指事先规定好循环几次。
   使用格式为:
for 变量 in LIST;do
 statement
done
 
例子:
  写一个脚本,显示每一位用户的默认shell;
     eg. 
        root: /bin/bash 
student: /bin/bash
 
脚本内容如下:
 
 
  
  1. #!/bin/bash 
  2. #Name:shell 
  3. #Description:for 
  4. #Author:Linli 
  5. #Version:0.0.1 
  6. #Datatime:06/17/12 17:20:00 
  7. #Usage: ./shell.sh  
  8.  
  9. ##### scripts ######## 
  10. for I in `cut -d: -f1 /etc/passwd`;do 
  11.   echo "$I : `grep "^$I" /etc/passwd | cut -d: -f7`" 
  12. done 
  13. ##### scripts ######## 
脚本执行结果如下:
 
  
  1. [root@www.magedu.com scripts]# ./oddsum.sh 
  2. root : /bin/bash 
  3. bin : /sbin/nologin 
  4. ...[其他显示内容省略了] 
 
 
四、break、continue、exit、return的用法
 
break :    中断循环,而后执行循环后面的语句
continue: 中断当前这一次循环,提前进入下一次循环
exit:   直接退出脚本
return:   用作自定义返回值