getopt/getopts命令

getopt/getopts 命令

命令的格式

getopt命令可以接受一系列任意形式的命令行选项和参数,并自动将它们转换成适当的格式。格式如下: getopt optstring parameters1 optstring是关键所在,它定义命令行有效的选项字母,还定义了那些选项字母需要参数值 getopt命令有一个更高级的版本叫做getopts

getopt 工作例子

#getopt ab:cd -a -b test1 -cd test2 test3 -a -b test1 -c -d -- test2 test312 optstring定义了四个有效选项字母:a,b,c,d.冒号(:)被放在了字母b后面,因为b选项需要一个参数值,当getopt命令运行时,它会检查提供的参数列表(-a -b test1 -cd test2 test3),并给予提供的optstring进行解析,它会自动讲-cd选项分成两个单独的选项,并插入双破折线来分割行中的额外参数。

在脚本中使用getopt

set命令的选项之一是双破折线(–),它会将命令行参数替换成shell中的各种变量 #/bin/bash ################################### # Extract command line options & values with getopt # set -- $(getopt -q ab:cd "$@") # echo while [ -n "$1" ] do case "$1" in -a) echo "Found the -a option" ;; -b) param="$2" echo "Found the -b option, with parameter value $param" shift ;; -c) echo "Found the -c option" ;; --) shift break ;; *) echo "$1 is not option";; esac shift done # count=1 for param in "$@" do echo "Parameter #$count: $param" count=$[ $count + 1 ] done #123456789101112131415161718192021222324252627282930 ####执行脚本,查看结果: #bash use_getopt.sh -ac Found the -a option Found the -c option123 ####加之前参数: #bash use_getopt.sh -a -b test1 -c test2 test3 Found the -a option Found the -b option, with parameter value 'test1' Found the -c option Parameter #1: 'test2' Parameter #2: 'test3'1234567 getopt 命令并不擅长处理带空格和引号的参数值

使用更高级的getopts

getopts格式如下: getopts optstring variables1 使用getopts例子如下: [root@log example]#cat use_getopts.sh #!/bin/bash ################################### # simple demonstration of the getopts command # echo while getopts :ab:c opt do case "$opt" in a) echo "Found the -a option" ;; b) echo "Found the -b option, with parameter value $OPTAVG" ;; c) echo "Found the -c option" ;; *) echo "Unknown option: $opt" ;; esac done 12345678910111213141516 执行getopts [root@log example]#bash use_getopts.sh -ab test1 -c Found the -a option Found the -b option, with parameter value Found the -c option 123456 getopts/getopt 处理命令行参数是一个相似而又复杂的事情,为此,C提供了getopt/getopt_long等函数, C++的boost提供了Options库,在shell中,处理此事的是getopts和getopt.getopts和getopt功能相似但又不完全相同,其中getopt是独立的可执行文件,而getopts是由Bash内置的。 先来看看参数传递的典型用法: * ./test.sh -a -b -c : 短选项,各选项不需参数 * ./test.sh -abc : 短选项,和上一种方法的效果一样,只是将所有的选项写在一起。 * ./test.sh -a args -b -c :短选项,其中-a需要参数,而-b -c不需参数。 * ./test.sh --a-long=args --b-long :长选项1234 使用getopts非常简单 #test.sh #!/bin/bash while getopts "a:bc" arg #选项后面的冒号表示该选项需要参数 do case $arg in a) echo "a's arg:$OPTARG" #参数存在$OPTARG中 ;; b) echo "b" ;; c) echo "c" ;; ?) #当有不认识的选项的时候arg为? echo "unkonw argument" exit 1 ;;1234567891011121314151617181920 现在就可以使用: ./test.sh -a arg -b -c 或 ./test.sh -a arg -bc 来加载了。 应该说绝大多数脚本使用该函数就可以了,如果需要支持长选项以及可选参数,那么就需要使用getopt. 下面是getopt自带的一个例子: #!/bin/bash # A small example program for using the new getopt(1) program. # This program will only work with bash(1) # An similar program using the tcsh(1) script language can be found # as parse.tcsh # Example input and output (from the bash prompt): # ./parse.bash -a par1 'another arg' --c-long 'wow!*\?' -cmore -b " very long " # Option a # Option c, no argument # Option c, argument `more' # Option b, argument ` very long ' # Remaining arguments: # --> `par1' # --> `another arg' # --> `wow!*\?' # Note that we use `"$@"' to let each command-line parameter expand to a # separate word. The quotes around `$@' are essential! # We need TEMP as the `eval set --' would nuke the return value of getopt. #-o表示短选项,两个冒号表示该选项有一个可选参数,可选参数必须紧贴选项 #如-carg 而不能是-c arg #--long表示长选项 #"$@"在上面解释过 # -n:出错时的信息 # -- :举一个例子比较好理解: #我们要创建一个名字为 "-f"的目录你会怎么办? # mkdir -f #不成功,因为-f会被mkdir当作选项来解析,这时就可以使用 # mkdir -- -f 这样-f就不会被作为选项。 TEMP=`getopt -o ab:c:: --long a-long,b-long:,c-long:: \ -n 'example.bash' -- "$@"` if [ $? != 0 ] ; then echo "Terminating..." >&2 ; exit 1 ; fi # Note the quotes around `$TEMP': they are essential! #set 会重新排列参数的顺序,也就是改变$1,$2...$n的值,这些值在getopt中重新排列过了 eval set -- "$TEMP" #经过getopt的处理,下面处理具体选项。 while true ; do case "$1" in -a|--a-long) echo "Option a" ; shift ;; -b|--b-long) echo "Option b, argument \`$2'" ; shift 2 ;; -c|--c-long) # c has an optional argument. As we are in quoted mode, # an empty parameter will be generated if its optional # argument is not found. case "$2" in "") echo "Option c, no argument"; shift 2 ;; *) echo "Option c, argument \`$2'" ; shift 2 ;; esac ;; --) shift ; break ;; *) echo "Internal error!" ; exit 1 ;; esac done echo "Remaining arguments:" for arg do echo '--> '"\`$arg'" ; done123456789101112131415161718192021222324252627282930313233343536373839404142434445464748495051525354555657585960616263 比如我们使用 ./test -a -b arg arg1 -c 你可以看到,命令行中多了个arg1参数,在经过getopt和set之后,命令行会变为: -a -b arg -c – arg1 1指向−a,1指向−a,1指向-a,2指向-b,3指向arg,3指向arg,3指向arg,4指向-c,$5指向–,而多出的arg1则被放到了最后。

最近更新的命令
网友补充 在这里补充本文不完善的地方,或是在此讨论和纠错,知识在于分享,您补充的资料会让更多人获得帮助!