• Shell 获取参数的方式


    Shell 获取参数的方式

    写shell脚本的时候,往往需要从外部获取参数,例如:

    $ sh demo.sh a
    

    那么如何将上面的参数a传到shell程序里面呢。
    最常用的是,$0 $1... $10,这些位置变量 其中$0是shell程序的名字,$1,$2...分别为第一个参数,第二个参数... 我们demo.sh 如下所示:

    $ cat demo.sh
    #! /bin/bash
    
    cat << EOF
         Usage: sh $0 $1
    EOF
    
    $ sh demo.sh a
     Usage: sh demo.sh a
    

    $开头的参数有:

    $0: 程序的名字
    $#: 变量的个数
    $@:所有的变量,即:$1...$最后,不包括程序的名字

    这有一个问题,当参数很多的时候,别人用你的程序时,交互性不是很好,别人还得记住脚本每一个参数的位置和作用,会很麻烦。这时可以加提示符:例如

    $ sh demo.sh -a A -b B -c C 
    

    那这个怎么实现呢? 实现的方式有两种 利用shiftgetopts

    $ cat demo.sh 
    #! /bin/bash
    
    while [ $# -gt 0 ];
    do
       case $1 in
       -a) echo "-a----$2"
           shift
           ;;
       -b) echo "-b----$2"
           shift
           ;;
       -c) echo "-c----$2"
           shift
           ;;
       esac
       shift
    done
    
    $ sh demo.sh -a A -b B -c C
    -a----A
    -b----B
    -c----C
    

    getopts函数则简化上面的选项处理过程。我们下面来看看它的使用方法。
    函数的第一个参数:合法选项字母的一个字符串, 如果字母后面后·:则表示必须要提供参数,这时getopts函数会将参数放到OPTARG中,另外一个变量是OPTIND代表下一个待处理参数的索引值。
    函数的第二个参数:变量名称,每次getopts被调用的时候,都会被更新,这个变量名字是没有限制的。getopts在找不到合法的选项的时候会将这个变量设置为一个问号。具体的实现如下所示:

    #! /bin/bash
    while getopts a:b:c: opt;
    do
    case $opt in
    a) echo "-a ---- $OPTARG"
       ;;
    b) echo "-b ---- $OPTARG"
       ;;
    c) echo "-c ---- $OPTARG"
       ;;
    ?) echo "$opt is an invalid option"
       ;;
    esac
    done
    
    $ sh demo.sh -a A -b B -c C -d
    -a ---- A
    -b ---- B
    -c ---- C
    demo.sh: illegal option -- d      --getopts输出的错误信息
    ? is an invalid option            --脚本判断输出的错误信息,这里将-d option设置为了? 
    

    但是getopts并不能处理长选项,这时可以借助getopt,大家可以man一下:

    NAME
    getopt - parse command options (enhanced)

    从基本解释可以看出,它是一个加强版的getopts,虽然getopts比它还多了一个s,但是论功力,还是远远不如getopt。这里有一个官网的例子:http://software.frodo.looijaard.name/getopt/docs/getopt-parse.bash。为了保持队形,稍微改写成解析-a -b -c --apple --banana --cat的demo.

    $ cat demo_getopt.sh 
    #! /bin/bash
    
    TEMP=$(getopt -o ab:c:: --long apple,banana:,cat:: -- "$@")
    if [ "$?" != "0" ]; then
        echo "Terminating..." >&2;
        exit 1
    fi
    
    eval set -- "$TEMP"    用"$TEMP"参数--前的字符串重置$1.$2.$3.$4...
    echo $TEMP 
    
    while true; do         解析$1.$2.$3.$4...
        case "$1" in
            -a|--apple) echo "Option $1, no argument"; shift 2;;
            -b|--banana) echo "Option $1 --> $2"; shift 2;;
            -c|--cat) 
                case "$2" in
                    "") echo "Option $1, no argument"; shift 2;;
                    *) echo "Option $1 --> $2"; shift 2;; 
                esac ;; 
            "--") shift; break;;
            *) echo "Internal error!"; exit 1;;
        esac
    done
    
    echo "Remaining arguments:"
    
    for arg in $@; do
        echo '-->' "$arg"
    done
    

    其中

    option ,表示后面不能跟参数
    option:,表示后面必须接参数
    option::,表示后面可接可不接

    运行结果

    $ sh demo_getopt.sh -a -b B -cC --apple --banana B testa testb
    -a -b 'B' -c 'C' --apple --banana 'B' -- 'testa' 'testb' 这是getopt解析的结果
    Option -a, no argument
    Option -b --> B
    Option -c --> C
    Option --apple, no argument
    Option --banana --> B
    Remaining arguments:
    --> testa
    --> testb
    
  • 相关阅读:
    MySQL基础学习笔记
    网络编程入门笔记
    JUC并发编程学习笔记
    育儿技巧
    无法下载安装文件,请检查internet连接
    用户 'NT ServiceSSISScaleOutMaster140' 登录失败
    Javascript中apply、call、bind
    JQuery 源码解析一
    docker容器中部署 kafka 和 elk
    查找库中所有表所有字段中某个指定的字符
  • 原文地址:https://www.cnblogs.com/zk47/p/3918086.html
Copyright © 2020-2023  润新知