美文网首页
shell高级用法

shell高级用法

作者: Hye_Lau | 来源:发表于2018-06-08 21:27 被阅读0次

    1.if语句

    1.1.回顾

    • 在运行脚本前,我们一般先对脚本的语法进行检查,如果脚本有bug,我们再调试脚本;
    • (1)语法检查:bash -n 脚本路径
    • (2)脚本调试:bash -x 脚本路径

    1.2.过程式编程语言的执行流程

    • 顺序执行
    • 选择执行
    • 循环执行
    • 选择执行
    1.2.1.&&,||
    command1 && command2:如果command1正确,也执行command2;如果command1不正确,不执行command2
    command1 || command2:如果command1正确,不执行command2;如果command1不正确,执行command2
    
    1.2.2.if语句
    • if单分支语句;
    • if多分支语句
    • if嵌套语句
    • (1)if 多分支语句格式(注意:多个分支只会执行一个,执行首先为真的分支)
    if  [ 条件1 ];then
            条件1为真执行这里的代码
    elif [ 条件2 ];then
            条件2为真执行这里的代码
    elif [ 条件3 ];then
            条件3为真执行这里的代码
    ......
    elif [ 条件n ];then
            条件n为真执行这里的代码
    else
            如果所有的条件都不满足时,执行这里的代码
    fi
    
    • (2)if嵌套语句格式
    if [ 条件 ];then
        if [ 条件 ];then
            执行这里的代码
        fi
    fi
    if [ 条件 ];then
        if [ 条件 ];then
            执行这里的代码
        fi
    else
        if [ 条件 ];then
            执行这里的代码
        fi
    fi
    

    1.3.示例

    • 1.通过脚本参数传递一个文件路径给脚本,判断此文件的类型;
    #!/bin/bash
    #
    if [ $# -lt 1 ];then
        echo "A argument is needed."
        exit 1
    fi
    
    if ! [ -e $1 ];then
        echo "No such file or directory."
        exit 2
    fi
    
    if [ -f $1 ];then
        echo "Common file"
    elif [ -d $1 ];then
        echo "Directory"
    elif [ -L $1 ];then
        echo "Symbolic link"
    elif [ -b $1 ];then
        echo "block special file"
    elif [  -c $1 ];then
        echo "character special file"
    elif [  -S $1 ];then
        echo "Socket file"
    else
        echo "Unknow"
    fi
    
    • 2.写一个脚本
      (1)传递一个参数给脚本,此参数为用户名 ;
      (2)根据其ID号来判断用户类型:0:管理员 ,1-499:系统用户,500+:为登入用户, 输出用户是那种类型的用户;
    #!/bin/bash
    #(1)传递一个参数给脚本,此参数为用户名
    # (2)根据其ID号来判断用户类型:0:管理员 ,1-999:系统用户,1000+:为登入用户
    
    if [ $# -lt 1 ]; then
        echo "A argument is needed."
        exit 1
    fi
    # 如何输入的用户名存在
    # 注意通过命令来判断成功与否不能加[]
    if id -u $1 &>/dev/null;then
        userid=$(id -u $1)
        if [ $userid -eq 0 ];then
            echo "Administrator"
        elif [ $userid -gt 1 -a $userid -lt 499 ];then
            echo " System user"
        elif [ $userid -ge 500 ];then
            echo "Login user"
        fi
    else
        echo "NO such user."    
    fi
    
    • 3.写一个脚本
      (1)列出如下菜单给用户
      disk) show disks info
      mem)show memory info
      cpu)show cpu info
      *)quit
      (2)提示用户给出自己的选择,而后显示对应其选择的相应系统信息
    #!/bin/bash
    cat << EOF
    disk) show disks info
    mem)show memory info
    cpu)show cpu info
    *)quit
    EOF
    
    read -p "Please input your option:" option
    
    # 如果用户输入的是大写,直接将大写转变为小写
    option=$(echo $option | tr [A-Z] [a-z])
    
    if [ $option == "disk" ]; then
        fdisk -l
    elif [ $option == "mem" ]; then
        free -m
    elif [ $option == "cpu" ]; then
        lscpu
    elif [ $option == "*" ]; then
        exit 1
    else
        echo "Wrong option"
    fi
    

    2.循环语句

    2.1.bash的循环分类:

    • for循环
    • while循环
    • until循环

    2.1.1.for 循环

    1.两种格式

    • 第一种格式:遍历列表
    • 第二种格式:控制变量
    (1)遍历列表
    for 变量 in 列表; do
        循环体
    done
    
    • 进入条件:只要列表中有元素,即可进入循环
    • 退出循环:列表中的元素遍历完成
    • 列表生成的方式
    1)直接取出 
        例如: user1 user2 user3
    2)整数列表 
        例如 {1..100}
        例如  `seq 1 2 100`  注意:中间的2表示步长
    3)返回列表的命令
        `ls /var/log/`
    4)glob
        例如: /var/log/*
    5)变量引用,如:@* ,
    
    示例
    • 示例1:
    #!/bin/bash
    for username in user1 user2 user3;do
        if id $username &>/dev/null;then
            echo "$username is already exists."
        else    
            useradd $username
            echo "Add &username success"
    done
    
    • 示例:2:求100内所有正整数之和;
    #!/bin/bash
    #
    declare -i sum=0
    
    for i in {1..100}; do
        sum=$[ $sum+$i ]
    done
    
    echo "$sum"  
    

    示例3:列出/var/log/目录下所有文件的类型;

    #!/bin/bash
    # 
    for option in /var/log/*; do
    
        if [ -f $option ];then
            echo "$option is Common file"
        elif [ -d $option ];then
            echo "$option is Directory"
        elif [ -L $option ];then
            echo "$option is Symbolic link"
        elif [ -b $option ];then
            echo "$option is block special file"
        elif [  -c $option ];then
            echo "$option is character special file"
        elif [  -S $option ];then
            echo "$option is Socket file"
        else
            echo "Unknow"
        fi
    done
    
    练习
    • 练习1:分别求100以内所有偶数之和,奇数之和;
    #!/bin/bash
    # 
    declare -i oven=0
    declare -i odd=0
    
    for i in {1..100}; do
        count=$[ $i % 2 ]
    
        if [[ $count == 0 ]]; then
            oven=$[ $oven + $i ]
        else
            odd=$[ $odd + $i ]
        fi
    done
    
    echo "oven is $oven"
    echo "odd is $odd"     
    
    • 练习2:计算当前用户的id之和;
    #!/bin/bash
    # 
    declare -i idcount=0
    userRow=$(wc -l /etc/passwd|cut -d" " -f1)
    
    # 这里不能使用{},作为列表,用seq:for i in `seq 1 $userRow`; do
    for i in $(seq 1 $userRow); do
        userName=$(cut -d: -f1 /etc/passwd|sed -n "$i"p)
        idcount=$[ $idcount + $(id -u $userName) ]
    done
    
    echo "$idcount"
    
    • 练习3:通过脚本参数传递一个目录,计算所有的文本文件的行数之和,并说明文件的总数;
    #/bin/bash
    #
    if [[ $# < 1 ]];then
        echo "A argument is needed."
        exit 1
    fi
    
    declare -i fileCounts=0
    declare -i rowsCounts=0
    
    # 文件数
    fileCounts=$( find $1 -type f | wc -l )
    
    for i in `seq 1 $fileCounts`; do
        #这里的egrep其实可以不要,也可以取出行数
        rowCount=$(find $1 -type f -exec wc -l {} \; | cut -d" " -f1 | sed -n "$i"p)
        rowsCounts=$[ $rowsCounts + $rowCount ]
    done
    echo "fileCounts is $fileCounts , rowsCounts is $rowsCounts"
    
    (2)控制变量
    for((i=1;i<10;i++));do
        进入循环代码
    done
    

    2.1.2.while 循环

    格式
    while CONDITION ; do 
    循环体 
    循环控制变量的修正表达式 
    done 
    
    • 进入条件:CONDITION测试为“真”
    • 退出条件:CONDITION测试为“假”
    示例
    • 示例1:求100以内所有正整数之和;
    #!/bin/bash
    #
    declare -i sum=0
    declare -i i=1
    
    while [ $i -le 100 ]; do
        sum=$[ $sum+$i ]
        let i++
    done
    
    echo "sum is $sum"
    

    2.1.3.until循环

    格式
    until CONDITION ; do 
    循环体 
    循环控制变量 
    done 
    
    • 进入条件:CONDITION测试为“假”
    • 退出条件:CONDITION测试为“真”
    示例
    • 示例1:求100以内所有正整数之和
    #!/bin/bash
    #
    declare -i sum=0
    declare -i i=1
    
    until [ $i -gt 100 ];do
        sum=$[ $sum+$i ]
        let i++
    done
    echo "sum to $sum"
    

    练习

    • 练习1:分别使用while for until实现,求100以内所有的偶数之和,100以内奇数之和;
    #!/bin/bash
    # 
    declare -i oven=0
    declare -i odd=0
    
    #for循环
    for i in  {1..100}; do
        count=$[ $i%2 ]
        if [ $count -eq 0 ]; then
            oven=$[ $oven+$i ]
        else
            odd=$[ $odd+$i ]
        fi
    done
    
    echo "odd is $odd"
    echo "oven is $oven"
    oven=0
    odd=0
    i=1
    
    #while循环
     while [ $i -le 100 ]; do
        count=$[ $i%2 ]
        if [ $count -eq 0 ]; then
            let oven+=$i
        else
            let odd+=$i
        fi
        let i++
     done
    
    echo "odd is $odd"
    echo "oven is $oven"
    oven=0
    odd=0
    i=1
    
    #until循环
    until [ $i -gt 100 ]; do
        count=$[ $i%2 ]
        if [ $count -eq 0 ]; then
            let oven+=$i
        else
            let odd+=$i
        fi
        let i++
    done
    
    echo "odd is $odd"
    echo "oven is $oven"
    
    • 练习2:创建9个用户,user101-user109;密码同用户名, 如果这些用户存在就删除,不存在就创建;
    #!/bin/bash
    
    for i in `seq 1 10`;do
            if id user10"$i" &> /dev/null;then
                    userdel -r user10"$i"
            else
                    useradd user10"$i"
                    echo "user10$i" | passwd --stdin user10"$i" &> /dev/null
                    echo "create user user10$i"
            fi
    done
    
    • 练习3:打印九九乘法表
    #!/bin/bash
    # 注意:这里的echo 的 -n选项表示不换行
    for((i=1;i<9;i++));do
        for((j=1;j<=$i;j++));do
            echo -n "$j X $i = $[ $j*$i ]  "
        done
        echo
    done
    
    • 练习4:打印逆序的九九乘法表
    #!/bin/bash
    #
    
    declare -i k=9
    while [ $k -ge 1 ]; do
            for i in `seq 1 $k| sort -n -r`;do
                echo -n "$i X $k = $[ $i*$k ]  "
            done
            echo ""
            let k--
    done
    

    3.循环控制语句

    • continue:跳出本次循环,进入下一轮循环;
    • break:跳出整个循环;
    • sleep:程序睡眠一个时间段;

    死循环:条件为true,永远为死循环

    3.1.continue语句

    格式
    while  [ 条件1 ]; do
        满足条件执行这里的代码
        if [ 条件2 ]; then
            # 跳出当前循环进入下一轮循环
            continue
        fi
        满足条件执行这里的代码
    done
    
    示例:
    • 求100以内所有的偶数之和;
    #/bin/bash
    # 
    declare -i evensum=0
    for i in {1..100}; do
        if [ $[ $i%2 ] -eq 1 ];then
            continue
        fi
        let evensum+=$i
    done
    echo "evensum is $evensum"
    
    #/bin/bash
    # 
    declare -i evensum=0
    declare -i i=0
    while [ $i -lt 100 ]; do
            let i++
        if [ $[ $i%2 ] -eq 1 ];then
            continue
        fi
        let evensum+=$i
    done
    echo "evensum is $evensum"
    

    3.2.break :直接跳出整个循环

    格式
    while [条件1]; do
        执行这里的代码
        if [条件2]; then
            break
        fi
        执行这里的代码
    done
    
    • 死循环:如何创建死循环
    while true;do
        循环体
    done
    
    • 退出方式:某个测试条件满足的时候,让循环体执行break命令就是
    示例:
    • 计算100以内奇数之和
    #/bin/bash
    # description
    # author
    declare -i oddsum=0
    declare -i i=1
    while true; do
        let oddsum=$oddsum+$i
        let i=$i+2
        if [ $i -gt 100 ];then
            break
        fi
    done
    echo "oddsum is $oddsum"
    

    3.3.sleep命令

    示例:
    • 每隔3秒钟到系统上获取已经登入的用户的信息,其中,如果sb用户登入了系统,则给QQ发送邮件,主题为“sb user is login”,并退出;
    #/bin/bash
    #
    while true; do
          if who | grep "^logstash\>" &> /dev/null; then
                 break;
          fi
          sleep 3
    done
    
    echo "$(date +"%F %T")logstash logged on" >> /tmp/users.log
    
    #/bin/bash
    #
    until who | grep "^logstash\>" &> /dev/null; do
          sleep 3
    done
     echo "$(date +"%F %T")logstash logged on" >> /tmp/users.log
    

    4.while和for循环的特殊用法

    4.1.while循环的特殊用法(遍历文件的行)

    格式
    while read VARIABLE;do
        循环体
    done < /PATH/TO/FILE
    

    意思是:依次读取/PATH/TO/FILE文件中的每一行,且将其赋值给VARIABLE变量

    示例:
    • 找出ID号为偶数的用户,显示其用户名、ID、及默认的shell;
    #/bin/bash
    # 
    while read line; do
    
            ID=$(echo $line|cut -d: -f3)
            if [ $[ $ID%2 ] -eq 0 ];then
                    username=$(echo $line | cut -d: -f1)
                    shell=$(echo $line | cut -d: -f7)
            echo "username is $username, ID is $ID , shell is $shell"
            fi
    done < /etc/passwd
    

    4.2.for循环的特殊用法

    格式
    for((控制变量初始化;条件判断表达式;控制变量修正语句));do
        循环体
    done
    
    示例:
    • 示例1:1到100的和
    #/bin/bash
    # 
    
    declare -i sum=0
    
    for((i=1;i<=100;i++));do
            let sum+=$i
    done
    echo "sum is $sum"
    
    • 示例2:打印九九乘法表
    #/bin/bash
    # 
    for((i=1;i<=9;i++));do
            for((j=1;j<=i;j++));do
                    echo -ne "${j}X${i}=$[ ${j}*${i} ]\t"
            done
            echo
    done
    

    5. case语句

    语法格式:

     case $VARAIBLE in
           PAT1)
                分支1
                 ;;
           PAT2)
                 分支2
                 ;;
                ...
             *)
                 分支n
                 ;;
    esac              
    

    case支持glob风格的通配符:

    *:任意长度的任意字符;
    ?:任意单个字符;
    []:任意单个字符;
    a|b:a或b;
    
    注意:
    • (1)每一个分支的两个分号一定不能少,如果没有两个分号,那么每一个case 的分支都会执行
    • (2)虽然这里的PAT可以只用模式匹配,但是只是支持glob模式的匹配,有:* ? [ ] [^ ] a|b 这几种方式

    示例:显示一个菜单给用户

    cpu)display cpu information
    mem)display memory information
    disk)display disk information
    quit)quit
    
    • (1)提示用户给出自己的选择
    • (2)正确的选择给出相应的信息,否则,提示用户,让用户重新选择正确的选项,直到用户选择正确为止
    #!/bin/bash
    #
    cat << EOF
    cpu)display cpu information
    mem)display memory information
    disk)display disk information
    quit)quit
    =============================
    EOF
    
    read -p "Enter your option:" option
    
    # 这里的while,通过read命令循环输入option,使得循环可以继续进行
    while [ "$option" != "cpu" -a "$option" != "mem" -a "$option" != "disk" -a "$option" != "quit" ]; do
        echo "please input cpu , mem , disk , quit "
        read -p "Enter your option:" option
    done
    
    if [ "$option" == "cpu" ];then
        lscpu
    elif [ "$option" == "mem" ];then
            free -m
    elif [ "$option" == "disk" ];then
            fdisk -l /dev/sd[a-z]
    elif [ "$option" == "quit" ];then
            echo "quit"
            exit 0
    fi
    
    • 将上述题目if else示例改写为case的判断,会使得代码的可读性增强
    #/bin/bash
    # 
    
    cat << EOF
    cpu)display cpu information
    mem)display memory information
    disk)display disk information
    quit)quit
    =============================
    EOF
    
    read -p "Enter your option:" option
    
    # 这里的while,通过read命令循环输入option,使得循环可以继续进行
    while [ "$option" != "cpu" -a "$option" != "mem" -a "$option" != "disk" -a "$option" != "quit" ]; do
        echo "please input cpu , mem , disk , quit "
        read -p "Enter your option:" option
    done
    
    case $option in
    cpu)
            lscpu ;;
    mem)
            free -m ;;
    disk)
            fdisk -l /dev/sd[a-z] ;;
    *)
            echo "quit"
            exit 0 ;;
    esac
    

    示例:写一个服务框架脚本;

    $lockfile,值/var/lock/subsys/SCRIPT_NAME

    • (1)此脚本可接受start,stop,restart,status四个参数之一;
    • (2)如果参数非此四者,则提示使用帮助后退出;
    • (3)start,则创建lockfile,并显示启动;stop则删除lockfile,并显示停止;restart,则先删除此文件再创建此文件,而后显示重启完成;status,如果lockfile存在,则显示running,否则,则显示为stopped.
     #!/bin/bash
    #
    # chkconfig: - 50 50
    # description: test service script
    prog=$(basename $0)
    lockfile=/var/lock/subsys/$prog
    case $1 in
    start)
          if [ -f $lockfile ]; then
                  echo "$prog is running yet."
          else
                  touch $lockfile
                  [ $? -eq 0 ] && echo "start $prog finshed."
          fi
          ;;
    stop)
          if [ -f $lockfile ]; then
                 rm -f $lockfile
                 [ $? -eq 0 ] && echo "start $prog finshed."
          else
               echo "$prog is running yet."
          fi
          ;;
    restart)
          if [ -f $lockfile ]; then
                  rm -f $lockfile
                  touch $lockfile
                  echo "start $prog finshed."
          else
                  touch -f $lockfile
                  echo "start $prog finshed."
          fi
          ;;
    status)
          if [ -f $lockfile ]; then
                  echo "$prog is running yet."
          else
                  echo "$prog is stopped."
          fi
          ;;
    *)
          echo "Usage:$prog {start|stop|restart|status}"
    esac
    

    6.函数:代码重用

    • 模块化编程
    • 结构化编程
    • 注意:定义函数的代码段不会自动执行,在调用时执行,所谓调用函数,在代码中给定函数名称即可,函数名出现的任何位置,在代码执行时候,都会自动替换为函数代码;

    6.1.语法格式:

    语法一:
     function f_name{
           函数体
      }
    
    语法二:
    f_name(){
         函数体
    }
    
    • 函数的生命周期:每次被调用时,被创建,返回时,终止
    • 其状态返回结果为函数体中运行的最后一条命令的状态结果
    • 自定义状态返回值,需要使用:return
    return [0-255] 
        0: 成功
        1-255:失败
    

    6.2.示例:

    • 示例1:给定一个用户名,取得用户名的ID号,和默认的shell
    #!/bin/bash
    #
    
    userinfo() {
        if id "$username" &> /dev/null; then
            grep "^$username\>" /etc/passwd | cut -d: -f3,7
        else
            echo "No such user."
        fi 
    }
    
    username=$1
    userinfo
    
    username=$2
    userinfo
    
    练习:

    写一个服务框架脚本名为create_file,接受start 、stop、 restart、 status 四个参数之一(这次用函数实现)

    • (1):如果参数非此四者,则提示使用帮助后退出
    • (2):如果传递start参数,则在/var/log目录下创建一个与脚本名相同的文件,并显示启动。
    • (3):如果传递stop参数,就在/var/log目录下删除一个与脚本名相同的文件 ,并显示停止。
    • (4):如果传递restart参数,就先删除再创建此文件,而后显示重启完成。
    • (5):如果传递status参数, 如果文件存在,则显示running, 否则显示为stopped
    #!/bin/bash
    #
    # chkconfig: - 50 50
    # description: test service script
    #
    prog=$(basename $0)
    FILE=/var/log/$prog
    
    start() {
        if [ -f $FILE ]; then
            echo "$prog is running yet."
        else
            touch $FILE
            [ $? -eq 0 ] && echo "start $prog OK."
        fi
    }
    
    stop() {
        if [ -f $FILE ]; then
            rm -f $FILE
            [ $? -eq 0 ] && echo "stop $prog finished."
        else
            echo "$prog is not running."
        fi
    }
    status() {
        if [ -f $FILE ]; then
            echo "$prog is running"
        else
            echo "$prog is stopped."
        fi
    }
    
    usage() {
        echo "Usage: $prog {start|stop|restart|status}"
    }
    
    case $1 in
    start)
        start ;;
    stop)
        stop ;;
    restart)
        stop
        start ;;
    status)
        status ;;
    *)
        usage
        exit 1 ;;
    esac
    

    6.3.函数的返回值分为两类

    1.函数的执行结果返回值
    • (1):使用echo或printf命令进行输出
    • (2):函数体中调用的命令的执行结果
    2.函数的退出状态码
    • (1):默认取决于函数体中执行的最后一条命令的退出状态码
    • (2):自定义:return (相当于脚本中的exit)

    6.4.函数可以接受参数

    • 在调用函数的时候可以给函数传递参数;
    • 在函数体中,可以使用$1, $2...引用传递给函数的参数,还可以使用$* 或$@调用所有的参数,$#表示传递的参数的个数;
    • 在调用函数时候,在函数名后面以空白字符分割给定参数列表即可,例如:functionName arg1 arg2 arg3 arg4...
    示例:
    • 示例1:添加10个用户,添加用户的功能使用函数实现,用户名作为参数传递给函数。这里有一个注意点,就是如果直接return $? ,在函数外面是不能拿到值的。
    #!/bin/bash
    #
    # 5: user exists
    
    addusers() {
        if id $1 &> /dev/null; then
            return 5
        else
            useradd $1
            retval=$?
            return $retval
        fi
    }
    
    for i in {1..10}; do
        addusers ${1}${i}
        # 在这里需要注意的是:每次函数的放回结果虽然可以使用$?来引用,但是在后面多次用到的时候,一定要将其使用一个变量保存起来,这里使用一个retval=$?保存了函数执行之后的状态码,以后为了规范起见,所有的函数返回的状态码都使用一个变量将其保存起来,如: variable=$? ,这样就不怕以后引用$?是出现错误。
        retval=$?
        if [ $retval -eq 0 ]; then
            echo "Add user ${1}${i} finished."
        elif [ $retval -eq 5 ]; then
            echo "user ${1}${i} exists."
        else
            echo "Unkown Error."
        fi
    done
    
    练习:
    • 练习1:写一个脚本:要求
    • (1)使用函数实现ping一个主机来测试主机的在线状态,主机地址通过参数传递给函数
    • (2)主程序:测试192.168.7.130 - 192.168.7.139 范围内的各个主机的在线状态
    • (3)如果主机在线,那么打印黄色的Online字符串,如果主机不在线打印红色的Offline字符串
    #!/bin/bash
    #
    if [ $# -lt 2 ];then
        echo "请输入两个主机地址作为IP地址的检测范围"
        exit 1
    fi
    START=$1
    END=$2
    
    # 检测IP的范围
    Ping(){
        ping -c1 -w1 192.168.7.13$1 &> /dev/null &&  echo -e "\E[1;33m 192.168.7.13$1 Online  \033[0m" || echo -e "\E[1;31m 192.168.7.13$1 Offline  \033[0m"
    }
    
    for i in `seq $1 $2`; do
        Ping $i
    done
    
    • 练习2:写一个脚本 :要求
      打印NN乘法表,使用函数实现, 例如:给脚本传递了一个11,那么就是打印11 X 11 的乘法表
    #!/bin/bash
    # 注意:这里的echo 的 -n选项表示不换行
    for((i=1;i<=$1;i++));do
            for((j=1;j<=$i;j++));do
                    echo -n "$j X $i = $[ $j*$i ]  "
            done
            echo
    done
    

    7.变量作用域

    • 局部变量:作用域是函数的生命周期,在函数结束时被自动销毁。定义局部变量的方法:local 变量=值
    • 本地变量:作用域是运行脚本的shell进程的生命周期,因此,其作用域范围是当前的shell脚本程序文件
    示例
    #!/bin/bash
    #
    name=tom
    
    # 记得以后为了避免函数中的变量与本地变量同名,如果同名,会使得具备变量修改本地变量的值,使得本地变量的指针直接指向函数中变量的存储空间。为了避免同名产生的错误,以后在函数中定义的变量都使用局部变量,在变量名前面加上一个local关键字
    setname() {
        local name=jerry
        echo "Function: $name"
    }
    
    setname
    echo "Shell: $name"
    

    8.递归

    • bash shell中和其他编程语言一样可以使用递归。那什么是递归:程序调用自身技巧称为递归( recursion)
    示例:
    • 写一个脚本,给脚本传递一个数值,脚本输出这个数值的阶层。例如:5!= 120
    #!/bin/bash
    
    func() {
        if [ $1 -eq 0 -o $1 -eq 1 ]; then
            echo 1
        else
            echo $[$1*$(func $[$1-1])]
        fi
    }
    
    func $1
    

    相关文章

      网友评论

          本文标题:shell高级用法

          本文链接:https://www.haomeiwen.com/subject/qjlmsftx.html