脚本乐园 Shell中命令行选项和参数的处理
在Linux的Shell中怎样处理tail -n 10 access.log这样的命令行选项呢?这是被别人问起的一个问题,好好学习了一下,进行总结如下:
在bash中,可以用以下三种方式来处理命令行参数,每种方式都有自己的应用场景。
1.直接处理,依次对$1,$2,...,$n进行解析,分别手工处理;
2.getopts来处理,单个字符选项的情况(如:-n 10 -f file.txt等选项);
3.getopt,可以处理单个字符选项,也可以处理长选项long-option(如:--prefix=/home等)。
总结:一般小脚本手工处理也许就够了,getopts能处理绝大多数的情况,getopt较复杂、功能也更强大。
下面分别进行简单的说明:
1.直接手工处理位置参数
必须要要知道几个变量,
* $0 :即命令本身,相当于C/C++中的argv[0]
* $1 :第一个参数.
* $2, $3, $4 ... :第2、3、4个参数,依次类推。
* $# 参数的个数,不包括命令本身
* $@ :参数本身的列表,也不包括命令本身
* $* :和$@相同,但"$*" 和 "$@"(加引号)并不同,"$*"将所有的参数解释成一个字符串,而"$@"是一个参数数组。
手工处理方式能满足多数的简单需求,配合shift使用也能构造出强大的功能,但处理复杂选项的时候建议用下面的两种方法。
给个实例吧(getargs.sh):
#!/bin/bash if [ $# -lt 1 ]; then echo "error.. need args" exit 1 fi echo "commond is $0" echo "args are:" for arg in "$@" do echo $arg done |
运行命令:./getargs.sh 11 22 cc
commond is ./getargs.sh
args are:
11
22
cc
2.getopts (Shell内置命令)
处理命令行参数是一个相似而又复杂的事情,为此,C提供了getopt/getopt_long等函数,C++的boost提供了Options库,在shell中,处理此事的是getopts和getopt.
先说一下getopts/getopt的区别吧,getopt是个外部binary文件,而getopts是shell builtin。
[admin@intlqa142055x ~]$ type getopt getopt is /usr/bin/getopt [admin@intlqa142055x ~]$ type getopts getopts is a shell builtin |
getopts不能直接处理长的选项(如:--prefix=/home等)
关于getopts的使用方法,可以man bash 搜索getopts
getopts有两个参数,第一个参数是一个字符串,包括字符和“:”,每一个字符都是一个有效的选项,如果字符后面带有“:”,表示这个字符有自己的参数。getopts从命令中获取这些参数,并且删去了“-”,并将其赋值在第二个参数中,如果带有自己参数,这个参数赋值在“OPTARG”中。提供getopts的shell内置了OPTARG这个变变,getopts修改了这个变量。
这里变量$OPTARG存储相应选项的参数,而$OPTIND总是存储原始$*中下一个要处理的元素位置。
while getopts ":a:bc" opt #第一个冒号表示忽略错误;字符后面的冒号表示该选项必须有自己的参数
代码实例(getopts.sh):
echo $* while getopts ":a:bc" opt do case $opt in a ) echo $OPTARG echo $OPTIND;; b ) echo "b $OPTIND";; c ) echo "c $OPTIND";; ? ) echo "error" exit 1;; esac done echo $OPTIND shift $(($OPTIND - 1)) #通过shift $(($OPTIND - 1))的处理,$*中就只保留了除去选项内容的参数,可以在其后进行正常的shell编程处理了。 echo $0 echo $* |
执行命令:./getopts.sh -a 11 -b -c
-a 11 -b -c
11
3
b 4
c 5
5
./getopts.sh
3.getopt(一个外部工具)
具体用用法可以 man getopt
#-o表示短选项,两个冒号表示该选项有一个可选参数,可选参数必须紧贴选项,如-carg 而不能是-c arg
#--long表示长选项
简单举个例子吧(getopt.sh):
#!/bin/bash
# A small example program for using the new getopt(1) program. # Example input and output (from the bash prompt): # Note that we use `"$@"' to let each command-line parameter expand to a #-o表示短选项,两个冒号表示该选项有一个可选参数,可选参数必须紧贴选项 TEMP=`getopt -o ab:c:: --long a-long,b-long:,c-long:: \ if [ $? != 0 ] ; then echo "Terminating..." >&2 ; exit 1 ; fi # Note the quotes around `$TEMP': they are essential! #经过getopt的处理,下面处理具体选项。 while true ; do |
运行命令:./getopt.sh --b-long abc -a -c33 remain
Option b, argument `abc'
Option a
Option c, argument `33'
Remaining arguments:
--> `remain'
参考资料:
http://www.cnblogs.com/FrankTan/archive/2010/03/01/1634516.html
http://www.orczhou.com/index.php/2010/04/linux-shell-getopt/
http://blog.csdn.net/flowingflying/archive/2010/01/03/5126066.aspx
脚本乐园 Shell中命令行选项和参数的处理的更多相关文章
- 【转】Bash Shell中命令行选项/参数处理
原文网址:http://www.cnblogs.com/FrankTan/archive/2010/03/01/1634516.html 0.引言 写程序的时候经常要处理命令行参数,本文描述在Bash ...
- Bash Shell中命令行选项/参数处理
0.引言 写程序的时候经常要处理命令行参数,本文描述在Bash下的命令行处理方式. 选项与参数: 如下一个命令行: ./test.sh -f config.conf -v --prefix=/home ...
- getopt:命令行选项、参数处理
在写shell脚本时经常会用到命令行选项.参数处理方式,如: ./test.sh -f config.conf -v --prefix=/home -f 为短选项,它需要一个参数,即config.co ...
- argparse - 命令行选项与参数解析(转)
argparse - 命令行选项与参数解析(译)Mar 30, 2013 原文:argparse – Command line option and argument parsing 译者:young ...
- 【makefile】make程序的命令行选项和参数
Make命令参数的典型序列如下所示: make [-f makefile文件名][选项][宏定义][目标] 这里用[]括起来的表示是可选的.命令行选项由破折号“–”指明,后面跟选项,如: make – ...
- argparse - 命令行选项与参数解析
argparse模块作为optparse的一个替代被添加到Python2.7.argparse的实现支持一些不易于添加到optparse以及要求向后不兼容API变化的特性,因此以一个新模块添加到标准库 ...
- Linux命令行选项及参数
1.main函数参数形式 int main(int argc , char *argv[] , char *env[]); //第一个参数argc代表命令行的参数个数 //第二个参数依次指向各个参数, ...
- python argparse模块:命令行选项及参数解析
位置参数:给一个例子: import argparse parser = argparse.ArgumentParser() parser.add_argument("echo") ...
- 【视频】Linux高级程序设计01.3命令行选项及参数
[课程笔记] [命令行参数] 选项:-l -a -i 参数:-l /home main 函数形式: int main(int argc, char *argv[]) main函数是有参数的,而且有返回 ...
随机推荐
- 如何查看eclipse中servlet跟jsp的版本
打开tomcat的lib 目录下,有两个JAR文件: jsp-api.jar servlet-api.jar .如果没有,那可能是你没有添加进来.解压这两个文件,用记事本分别打开META-INF下的M ...
- java 基本数据类型 回顾
- 一个简单的以User权限启动外部应用程序(用NetUserAdd函数和USER_INFO_1结构体动态添加用户,然后用CreateProcessWithLogonW启动程序)
版权声明:本文为博主原创文章,未经博主允许不得转载. BOOL ExecuteAsUser(LPCWSTR lpszUserName, LPCWSTR lpszPassword, LPCWSTR lp ...
- RHEL7-使用Apache服务部署静态网站
1. 安装Apache服务程序 1.1 在虚拟机中选中光盘镜像,并设置连接 1.2 将光盘设备挂载到/media/cdrom目录 [root@localhost ~]# mkdir -p /media ...
- Android 【问题汇总】列表数组越界的问题
遇到了一个诡异的问题,ListView发生数组越界(偶尔会),程序崩溃. 错误信息如下: W/dalvikvm( ): threadid=: thread exiting with uncaught ...
- WPF多线程UI更新——两种方法
WPF多线程UI更新——两种方法 前言 在WPF中,在使用多线程在后台进行计算限制的异步操作的时候,如果在后台线程中对UI进行了修改,则会出现一个错误:(调用线程无法访问此对象,因为另一个线程拥有该对 ...
- !! This tutorial was designed to help you with installation and configuration of OpenCV4Android SDK.
ref: http://docs.opencv.org/doc/tutorials/introduction/android_binary_package/O4A_SDK.html#running-o ...
- IOS 改变导航栏返回按钮的标题
IOS 改变导航栏返回按钮的标题 下午又找到了一个新的方法 这个方法不错 暂时没有发现异常的地方. 新写的App中需要使用UINavigationController对各个页面进行导航,但由于第一 ...
- [置顶] 炎炎夏日,给你一次极爽的开发体验!——统一开发环境功能升级优化,正式上线V2.0!
作为中国移动应用运行托管平台(MM应用引擎)的开发部署工具,统一开发环境(UDE)在原HTML5跨平台开发功能基础上优化升级,新增跨平台编译(Android/iOS)和云端托管服务,正式上线2.0版本 ...
- android sqlite 一次创建多个表
package com.yangguangfu.database; import android.content.Context; import android.database.sqlite.SQL ...