预备知识:
1.getopt()
getopt在UNIX下的命令列程式特别好用,特别是在你有许多参数要加入时。
表头文件:#i nclude <unistd.h>
函数声明:int getopt(int argc, char * const argv[], const char *optstring);
函数说明:getopt()用来分析命令行参数。参数argc和argv是由main()传递的参数个数和内容。参数optstring 则代表欲处理的选项字符串。此函数会返回在argv 中下一个的选项字母,此字母会对应参数optstring 中的字母。如果选项字符串里的字母后接着冒号“:”,则表示还有相关的参数,全域变量optarg 即会指向此额外参数。如果getopt()找不到符合的参数则会印出错信息,并将全域变量optopt设为“?”字符,如果不希望getopt()印出错 信息,则只要将全域变量opterr设为0即可。
返回值:如果找到符合的参数则返回此参数字母,如果参数不包含在参数optstring 的选项字母则返回“?”字符,分析结束则返回-1。
2.getopt_long()
函数原型
int getopt_long(int argc, char * const argv[], const char *optstring, const struct option *longopts, int *longindex);
分析命令行选项是一件繁琐的工作。幸运的是GNU C库提供了一个函数使你在处理这项工作时能简单一点。这个函数是getopt_long,它能理解长短两种选项。
要使用getopt_long,你必须提供两个数据结构。头一个是包含有效短选项的字符串,每个选项一个字符。需要参数的选项后面放一个冒号。比如我们的程序,这个字符串为ho:v,表示有效选项是-h,-o与-v并且第二个参数-o后面需要一个参数。
要 指定可用的长选项,你要构建一个option结构的数组。每个元素对应一个长选项,并有四个域。一般情况下,第一个域是长选项的名字(一个字符串,不包含 两个连字符),第二个域如果是1表示这个选项接受一个参数,如果为0表示没有参数。第三个是NULL,第四个是一个字符常量指出与这个长选项对应的短选 项。最后的数组元素全部域应该都为0.
调用getopt_long时,向它传递main的参数argc,argv,描述短选项的字符串与描述长选项的option结构数组。
*每调用getopt_long一次,它分析一个选项,返回这个选项的短选项字母,如果没有发现选项则返回-1.
*典型情况下,我们在一个循环中调用getopt_long,来处理所有用户指定的选项,并通过一个switch语句来处理特别的选项。
*如果getopt_long遇到一个无效选项,它将打印一个错误信息并返回字符'?'。大多数程序将因此退出,并显示用法提示。
*在处理需要参数的选项时,全局变量optarg指向这个参数正文。
*当getopt_long完全全部选项分析时,全局变量optind包含第一个非选项参数在argv中的索引。
optstring中的指定的内容的意义(例如getopt(argc, argv, "ab:c:de::"):
-
单个字符,表示选项,(如上例中的abcde各为一个选项)
-
单个字符后接一个冒号:表示该选项后必须跟一个参数。参数紧跟在选项后或者以空格隔开。该参数的指针赋给optarg。(如上例中的b:c:)
-
单个字符后跟两个冒号,表示该选项后必须跟一个参数。参数必须紧跟在选项后不能以空格隔开。该参数的指针赋给optarg。(如上例中的e::)
getopt函数所设置的全局变量如下:
-
optarg : 指向当前选项参数(如果有)的指针
-
optind : 再次调用 getopt() 时的下一个 argv 指针的索引。
-
opterr : 是否打印出错信息,如果不希望getopt()印出错信息,则只要将全域变量opterr设为0即可。
-
optopt : 最后一个已知选项。
程序清单1(getopt函数):
- #include <stdio.h> //printf()
- #include <stdlib.h> //exit(1)
- #include <unistd.h> //getopt()
- int main(int argc,char *argv[])
- {
- char ch;
- if(argc == 1)
- {
- fprintf(stderr,"Usage:%s [-a value][-b value][-c value][-d] arglist...n",argv[0]);
- exit(1);
- }
- while((ch = getopt(argc,argv,"a:b:c:d")) != EOF)
- {
- switch(ch)
- {
- case 'a':
- printf("a option:%sn",optarg);
- break;
- case 'b':
- printf("b option:%sn",optarg);
- break;
- case 'c':
- printf("c option:%sn",optarg);
- break;
- case 'd':
- printf("d option:%sn",optarg);
- break;
- case '?':
- printf("illegal option:%sn",optarg);
- break;
- }
- }
- exit(0);
- }
编译运行程序及输出结果如下:
obe-240 eagle/test> gcc -o getopt getopt.c
obe-240 eagle/test> ./getopt
Usage:./getopt [-a value][-b value][-c value][-d] arglist...
obe-240 eagle/test> ./getopt -a hello
a option:hello
obe-240 eagle/test> ./getopt -b world
b option:world
obe-240 eagle/test> ./getopt -c eagle
c option:eagle
obe-240 eagle/test> ./getopt -d
d option:(null)
obe-240 eagle/test> ./getopt first seconde -a helloworld #Attention!#
a option:helloworld
obe-240 eagle/test> ./getopt -e
./getopt: invalid option -- e
illegal option:(null)
程序清单(getopt_long函数):
- #include <stdio.h> //for printf
- #include <stdlib.h> //for exit
- #include <getopt.h> //for getopt_long and struct option
- const char *program_name;
- void print_usage(FILE *stream,int exit_code)
- {
- fprintf(stream,"Usage:%s options [inputfile...]/n",program_name);
- fprintf(stream,
- "-h --help: Display this usage information./n"
- "-o --output filename: Write output to file./n "
- "-v --verbose: Print verbose message./n");
- exit(exit_code);
- }
- int main(int argc,char *argv[])
- {
- int option;
- program_name = argv[0];
- const char* const short_options = "ho:v";
- const char* output_filename = NULL;
- int verbose = 0;
- const struct option long_options[]=
- {
- {"help",0,NULL,'h'},
- {"output",1,NULL,'o'},
- {"verbose",0,NULL,'v'},
- {NULL,0,NULL,0}
- };
- do
- {
- option = getopt_long(argc,argv,short_options,long_options,NULL);
- switch(option)
- {
- case 'h':
- print_usage(stdout,0);
- case 'o':
- output_filename = optarg;
- break;
- case 'v':
- verbose = 1;
- break;
- case '?':
- print_usage(stderr,1);
- case -1: //Done with options
- break;
- default: //Something else unexpected
- abort();
- }
- }while(option != -1);
- if(verbose)
- {
- int i;
- for(i=optind;i<argc;++i)
- {
- printf("Argument[%d]:%s/n",i,argv[i]);
- }
- }
- exit(0);
- }
编译并运行程序:
longmenyu@longmenyu-Vostro-1088:~/code$ gcc -o getopt_long getopt_long.c
longmenyu@longmenyu-Vostro-1088:~/code$ ./getopt_long -h
Usage:./getopt_long options [inputfile...]
-h --help: Display this usage information.
-o --output filename: Write output to file.
-v --verbose: Print verbose message.
longmenyu@longmenyu-Vostro-1088:~/code$ ./getopt_long -o
./getopt_long: option requires an argument -- 'o'
Usage:./getopt_long options [inputfile...]
-h --help: Display this usage information.
-o --output filename: Write output to file.
-v --verbose: Print verbose message.
longmenyu@longmenyu-Vostro-1088:~/code$ ./getopt_long -v hello world eagle
Argument[2]:hello
Argument[3]:world
Argument[4]:eagle