www.icesr.com
IT运维工程师的摇篮

bash shell脚本编程学习总结

shell脚本编程

<code>编译器-------解释器  
静态语言:编译型语言,强类型(变量);事先转换成可执行格式。C/C++/JAVA/C#
动态语言:解释型语言,弱类型。边解释变执行。PHP,SHELL,python,perl
面向过程:shell,c;面向对象:java,python,perl,c++
变量赋值:VAR_NAME = VALUE;

bash变量类型:
    环境变量:作用域为当前shell进程及其子进程。
        export VARNAME=VALUE或者 VARNAME=VALUE export VARNAME "导出"定义为环境变量。
        脚本在执行时候启动一个子shell进程:
        [root@iZ233y80y23Z ~]# NAME=LINJUNBIN
        [root@iZ233y80y23Z ~]# export NAME
        [root@iZ233y80y23Z ~]# echo $NAME
        LINJUNBIN
        [root@iZ233y80y23Z ~]# bash   //切换到子shell;
        [root@iZ233y80y23Z ~]# echo $NAME  //该环境变量依然有效。
        LINJUNBIN

    本地变量(局部变量):
        整个bash进程:本地变量:VARNAME=VALUE 
        局部变量:作用域为当前代码段有效。local VARNAME=VALUE
    位置变量:
        $1,$2,....
    特殊变量:(bash内置):$?:上一个命令的执行状态返回值状态值;
        程序执行一般有两种返回值;执行状态$?=0-255
        0:正确执行;1-255:错误执行;
        1,2,127:系统预留。
        $?:上次命令执行返回状态码;
        $#:参数的个数
        $*:参数列表
        $@:参数列表            

引用变量:${VAR_NAME},引用该变量。
    [root@iZ233y80y23Z ~]# echo "there are some ${ANIMAL}s."
    there are some PIGs.
    [root@iZ233y80y23Z ~]# echo 'there are some ${ANIMAL}s.'
    there are some ${ANIMAL}s.
    注意:''单引号和""双引号的区别。

输出重定向:
    &gt;:&gt;&gt;:2&gt;:2&gt;&gt;,&amp;&gt;  
输入:
    /dev/null:软件设备;/dev/null:数据黑洞;
    eg:判断是否含有某个用户。
        [root@iZ233y80y23Z ~]# id student &amp;&gt; /dev/null
        [root@iZ233y80y23Z ~]# echo $?
        1
撤销变量:
    unset VARNAME不用加$;
查看变量:
    使用set命令;set:包含环境变量和本地变量;
    查看环境变量:printenv ,env, export;三个都可以。
eg:
    [root@iZ233y80y23Z ~]# ANIMALS=pig
    [root@iZ233y80y23Z ~]# ANIMALS=$ANIMALS:goat
    [root@iZ233y80y23Z ~]# echo $ANIMALS
    pig:goat    
脚本:命令的堆砌,       
判断用户是否存在:id user1 &amp;&gt; /dev/null &amp;&amp; echo "hello user1";
    [root@iZ233y80y23Z test]# id root &amp;&gt; /dev/null &amp;&amp; echo 'root'
    root
</code>

shell条件判断

<code>判断执行结果$?来判断执行的状态码来判断执行是否成功或者失败。
整数测试:
    -eq:测试两个整数是否相等;
    -ne:测试两个整数是否不等,不等,为真;相等,为假;
    -gt:测试一个数是否大于另一个数;
    -lt:测试一个数是否小于另一个数;
    -ge:大于或者等于;
    -le:小于或者等于;
    eg:
            [root@iZ233y80y23Z test]# A=3
            [root@iZ233y80y23Z test]# B=4
            [root@iZ233y80y23Z test]# [ $A -eq $B ]
            [root@iZ233y80y23Z test]# echo $?
            1
            [root@iZ233y80y23Z test]# B=3
            [root@iZ233y80y23Z test]# [ $A -eq $B ]
            [root@iZ233y80y23Z test]# echo $?
        0
字符测试:
文件测试:

条件测试表达式:注意:两边要空格。
    [ expression表达式 ],[[ expression ]] , test expression
表达式:

命令间的逻辑关系;
    逻辑与:&amp;&amp;,第一个条件为假第二个条件不用执行,两个都必须为真。
    逻辑或:|| 第一个条件为假,第二个条件必须得判断。两个中一个为真就可以。
    eg:如果用户user6不存在,就添加用户user6
        ! id user6 &amp;&gt; /dev/null &amp;&amp; useradd user6
        id user6 &amp;&gt; /dev/null || useradd user6
LINE=`wc -l /etc/inittab`;将这个命令运行结果放在变量中。   
eg:如果文件/etc/inittab文件的行数大于100,就显示好大的文件,否则显示小文件。
        [root@iZ233y80y23Z test]# cat souce.sh 
        #!/bin/bash     
        LINES=`wc -l /etc/inittab`      
        echo $LINES        
        FINLINES=`echo $LINES | cut -d' ' -f1`
        echo $FINLINES;    

        [ $FINLINES -gt 100 ] &amp;&amp; echo "/etc/inittab is a big file." || echo "/etc/inittab is a small file"

        [root@iZ233y80y23Z test]# bash souce.sh 
        17 /etc/inittab
        17
        /etc/inittab is a small fi

eg:为系统添加用户:
`! id user1 &amp;&gt; /dev/null &amp;&amp; useradd user1 &amp;&amp; echo "user1" | passwd --stdin user1 &amp;&gt; /dev/null || echo 'user1 exists`
    添加完用户,管道到passwd。进行设置密码;同时输出总行数。
    [root@iZ233y80y23Z test]# bash addUser.sh 
    user1 exists
    39
    [root@iZ233y80y23Z test]# cat addUser.sh 
    #!/bin/bash 
    ! id user1 &amp;&gt; /dev/null &amp;&amp; useradd user1 &amp;&amp; echo "user1" | passwd --stdin user1 &amp;&gt; /dev/null || echo 'user1 exists'
    ! id user2 &amp;&gt; /dev/null &amp;&amp; useradd user2 &amp;&amp; echo "user2" | passwd --stdin user2 &amp;&gt; /dev/null || echo 'user2 exists'
    ! id user3 &amp;&gt; /dev/null &amp;&amp; useradd user3 &amp;&amp; echo "user3" | passwd --stdin user3 &amp;&gt; /dev/null || echo 'user3 exists'     
    #获取总行数
    LINES=`wc -l /etc/passwd | cut -d' ' -f1`
    echo $LINES;

    eg:
    #判断当前用户是否为root用户;
            [root@iZ233y80y23Z test]# bash is_root.sh 
            is root
            [root@iZ233y80y23Z test]# cat is_root.sh 
            #!/bin/bash
            USER_UID=`id -u`;
            [ $USER_UID -eq 0 ] &amp;&amp; echo 'is root' || echo "is not root and this uid is ${UID}"
        注意:报错is_root.sh: line 2: UID: readonly variable,原来是UID变量设置和环境变量重名,主要变量命名。
</code>

if条件判断

<code>单分支的if语句:
    if 判断条件 
    then 
        statement1;statement2; 
    fi
双分支if语句:
    if 判断条件; then 
        statement1;statement2;... 
    else 
        statement3;statement4;... 
    fi
多分支if语句
    if 条件判断1; then
        statement1;...
    elif 判断条件2; then
        statement2;...
    elif 判断条件3; then
        statement3;...
    ...
    else
        statement4;...
    fi

eg:
    #判断某个用户是否存在:
    [root@iZ233y80y23Z test]# bash user.sh 
    user12 IS NOT exists
    [root@iZ233y80y23Z test]# cat user.sh 
    #!/bin/bash 
    NAME=user12;        
    if id $NAME &amp;&gt; /dev/null; then
    echo "$NAME is exists"
    else
    echo "$NAME IS NOT exists"
    fi
    #如果用户存在就显示存在,如果不存在就进行添加;

eg:
#判断当前系统是否有用户的默认shell为bash:如果有,就显示多少个,否则就显示没有这类用户
        [root@iZ233y80y23Z test]# ./is_bash.sh 
        the shells of 10 users is bash shell
        [root@iZ233y80y23Z test]# cat is_bash.sh 
        #!/bin/bash
        #获取默认的shell为bash
        grep "bash$" /etc/passwd &amp;&gt; /dev/null;
        RETVAL=$?;
        if [ $RETVAL -eq 0 ]; then
          USERS=`grep "/&lt;bash$" /etc/passwd | wc -l`
          echo "the shells of $USERS users is bash shell";
        else
         echo "no bash user"
        fi 
        [root@iZ233y80y23Z test]# 

#验证/etc/inittab这个文件有没有空白行,多少空白行
        [root@iZ233y80y23Z test]# cat has_space.sh 
        #!/bin/bash 
        grep "^$" /etc/inittab &amp;&gt; /dev/null;
        HAS_SPACE=$?
        if [ $HAS_SPACE -eq 0 ] ; then
        SPACES=`grep "^$" /etc/inittab | wc -l`;
        echo "total SPACES is $SPACES LINES";
        else
        echo "no any spaces in /etc/inittab";
        fi
        [root@iZ233y80y23Z test]# 
    注意:等号两边不能有空格;

#验证用户的uid是否等于GID,两种实现方式
        [root@iZ233y80y23Z test]# cat uid_eq.sh 
        #!/bin/bash
        USERNAME=user1
        #USERID=`id -u $USERNAME`;
        USERID=`grep "^user1" /etc/passwd | cut -d: -f3`
        GROUPID=`grep "^user1" /etc/passwd | cut -d: -f4`
        #GROUPID=`id -g $USERNAME`;

        if [ $USERID -eq $GROUPID ] ; then
        echo 'Good guy';
        else
        echo 'Bad guy';
        fi
#注意:date +%s表示时间戳中1970开始的秒数;man date
echo $HISTSIZE;

#给定一个文件测试其是否存在  
#单步执行;bash -x
    eg:测试脚本的执行过程。bash -x
        [root@iZ233y80y23Z test]# bash -x file_test.sh 
        + FILE=/etc/inittab
        + '[' -e /etc/inittab ']'
        + echo OK
        OK
        [root@iZ233y80y23Z test]#

#给定一个文件,如果是否普通文件,就显示,如果是目录就显示,否则显示无法辨别该文件。
    [root@iZ233y80y23Z test]# ./file_test.sh 
    common file
    [root@iZ233y80y23Z test]# cat file_test.sh 
    #!/bin/bash

    FILE=/etc/inittab

    if [ ! -e $FILE ]; then
    echo 'no such file';
    exit 6;
    fi      
    if [ -f $FILE ]; then
    echo 'common file';
    elif [ -d $FILE ]; then
    echo 'directory';
    else
    echo 'unknown';
    fi
    注意:判断符!后面必须要有空格;
</code>

shell中进行算术运算

<code>shell中默认所有的变量都是字符串;
    [root@iZ233y80y23Z test]# A=3
    [root@iZ233y80y23Z test]# B=4
    [root@iZ233y80y23Z test]# echo $A+$B
    3+4
一般使用1,2,3这三种方法:
1、算术运算let:
    let C=$A+$B
2、$[算术运算表达式]
    C=$[$A+$B]
3、$((算术运算表达式))
    C=$(($A+$B))
4、expr 算术运算表达式,表达式中各操作数和运算符之间要有空格,而且使用命令引用
    F=`expr $A + $B`
5、使用运算器bc   
</code>

退出脚本

<code>exit:退出脚本;  
exit n;n为退出状态码;
如果脚本没有明确定义退出状态码,那么,最后一条命令的退出码即为脚本的退出状态码;
</code>

测试方法

<code>使用中括号测试法:
[ expression ]:两边记得要用空格,命令测试法;
[[ expression ]]:关键字测试法;
test expression:
只有使用-gt,-le,-ne,-eq,-ge,-lt:需要加上中括号,其他的不一定需要加中括号。
if `grep "^$USERNAME/&gt;" /etc/passwd` ; then

文件测试:
    -e FILE:文件是否存在。
    -f FILE:测试文件是否为普通文件
    -d FILE:测试指定路径是否为目录;
    -r FILE:测试当前用户对指定文件是否有读权限
    -w FILE:测试当前用户对指定文件是否有写权限
    -x FILE:测试当前用户对指定文件是否有执行权限
    eg:
    [ -e /etc/inittab ] ,[ -x /etc/rc.d/rc.sysinit ]
        [root@iZ233y80y23Z test]# ./exitst_file.sh 
        NO /etc/iniittab
        [root@iZ233y80y23Z test]# cat exitst_file.sh 
        #!/bin/bash

        FILE=/etc/iniittab
        if [ ! -e $FILE ] ; then
          echo "NO $FILE"
          exit 8;
        fi

圆整:丢弃小数点后面内容;/
显示历史命令:
    [root@iZ233y80y23Z test]# history | tail -1 | cut -d' ' -f2
    1012    
</code>

位置变量(参数)

<code>位置变量$1,$2,...
./file_test.sh /etc/fstab /etc/inittab;
$1:/etc/fstab;   $2:/etc/inittab;
shift:将参数列表中第一个参数弹出;相当于数组中的shift弹出第一个元素;
shift n:表示一次弹出n个参数;

#判定:接收一个参数,如果一个存在的文件就显示OK,如果不存在就显示no such file
    eg:$#:显示所有参数个数;$*:参数列表 $@:参数列表;
            [root@iZ233y80y23Z test]# ./exitst_file.sh /etc/inittab /ffff /ttddd
            3
            /etc/inittab /ffff /ttddd
            /etc/inittab /ffff /ttddd
            OK
            [root@iZ233y80y23Z test]# cat exitst_file.sh 
            #!/bin/bash
            echo $#
            echo $*
            echo $@

            if [ ! $1 ]; then
             echo 'please add parame file'; 
            exit;
            fi

            if [ -e $1 ] ; then
              echo "OK"
            else
              echo "no such file";
            fi
            [root@iZ233y80y23Z test]#

#测试shift
        [root@iZ233y80y23Z test]# ./shift.sh 1 2 3 4 5
        5
        1
        2
        4
        [root@iZ233y80y23Z test]# cat shift.sh 
        #!/bin/bash

        echo $#;
        echo $1;
        shift
        echo $1;
        shift 2
        echo $1
</code>

未经允许不得转载:冰点网络 » bash shell脚本编程学习总结

分享到:更多 ()

评论 抢沙发

评论前必须登录!