使用 getopt() 进行命令行处理
2008-09-05 09:59
232 查看
在编写新程序时,首先遇到的障碍之一就是如何处理控制其行为的命令行参数。这包括从命令行传递给您程序的
清单 1. 声明
第一种方式使用的是指向
当 C 运行时库的程序启动代码调用您的
例如,如果使用参数
清单 2. argv 的内容
一个程序仅有一组命令行参数,因此我要将此信息存储在记录选项和设置的全局结构中。对程序有意义的要跟踪的任何内容都可以记录到此结构中,我将使用结构来帮助减少全局变量的数量。正如我在网络服务设计文章(请参阅参考资料)所提到的,全局变量非常不适合用于线程化编程中,因此要谨慎使用。
示例代码将演示一个假想的 doc2html 程序的命令行处理。该 doc2html 程序将某种类型的文档转换为 HTML,具体由用户指定的命令行选项控制。它支持以下选项:
将使用其他文件名称来作为输入文档。
您还将支持
简单命令行处理:
清单 3.
给定了命令参数的数量 (
对于每个选项,选项字符串 (
可以重复调用
让我们对 getopt_demo 项目的代码进行一下深入分析;为了方便起见,我在此处将此代码拆分为多个部分,但您可以在可下载源代码部分获得完整的代码(请参见下载)。
在清单 4 中,可以看到系统演示程序所使用的系统头文件;标准
清单 4. 系统头文件
清单 5 显示了我所创建的
每个命令行选择都有一个对应的选项,而其他变量用于存储输出文件名、指向输入文件列表的指针和输入文件数量。
main()函数的一个整数计数(通常名为 argc)和一个指向字符串的指针数组(通常名为 argv).可以采用两种实质一样的方式声明标注
main()函数,如清单 1 中所示。
清单 1. 声明
main()函数的两种方式
int main( int argc, char *argv[] ); int main( int argc, char **argv ); |
char指针数组,现在似乎很流行这种方式,比第二种方式(其指针指向多个指向
char的指针)略微清楚一些。由于某些原因,我使用第二种方式的时间更多一些,这可能源于我在高中时艰难学习 C 指针的经历。对于所有的用途和目的,这两种方法都是一样的,因此可以使用其中您自己最喜欢的方式。
当 C 运行时库的程序启动代码调用您的
main()时,已经对命令行进行了处理。
argc参数包含参数的计数值,而
argv包含指向这些参数的指针数组。对于 C 运行时库,arguments 是程序的名称,程序名后的任何内容都应该使用空格加以分隔。
例如,如果使用参数
-v bar www.ibm.com运行一个名为 foo 程序,您的 argc 将设置为 4,
argv的设置情况将如清单 2 中所示
清单 2. argv 的内容
argv[0] - foo argv[1] - -v argv[2] - bar argv[3] - http://www.ibm.com/ |
示例代码将演示一个假想的 doc2html 程序的命令行处理。该 doc2html 程序将某种类型的文档转换为 HTML,具体由用户指定的命令行选项控制。它支持以下选项:
-I——不创建关键字索引。
-l lang——转换为使用语言代码
lang指定的语言。
-o outfile.html——将经过转换的文档写入到 outfile.html,而不是打印到标准输出。
-v——进行转换时提供详细信息;可以多次指定,以提高诊断级别。
将使用其他文件名称来作为输入文档。
您还将支持
-h和
-?,以打印帮助消息来提示各个选项的用途。
简单命令行处理:
getopt()
getopt()函数位于 unistd.h 系统头文件中,其原型如清单 3 中所示:
清单 3.
getopt()原型
int getopt( int argc, char *const argv[], const char *optstring ); |
argc)、指向这些参数的数组 (
argv) 和选项字符串 (
optstring) 后,
getopt()将返回第一个选项,并设置一些全局变量。使用相同的参数再次调用该函数时,它将返回下一个选项,并设置相应的全局变量。如果不再有识别到的选项,将返回
-1,此任务就完成了。
getopt()所设置的全局变量包括:
optarg——指向当前选项参数(如果有)的指针。
optind——再次调用
getopt()时的下一个 argv 指针的索引。
optopt——最后一个已知选项。
对于每个选项,选项字符串 (
optstring) 中都包含一个对应的字符。具有参数的选项(如示例中的
-l和
-o选项)后面跟有一个
:字符。示例所使用的
optstring为
Il:o:vh?(前面提到,还要支持最后两个用于打印程序的使用方法消息的选项)。
可以重复调用
getopt(),直到其返回
-1为止;任何剩下的命令行参数通常视为文件名或程序相应的其他内容。
getopt()的使用
让我们对 getopt_demo 项目的代码进行一下深入分析;为了方便起见,我在此处将此代码拆分为多个部分,但您可以在可下载源代码部分获得完整的代码(请参见下载)。
在清单 4 中,可以看到系统演示程序所使用的系统头文件;标准
stdio.h提供标准 I/O 函数原型,
stdlib.h提供
EXIT_SUCCESS和
EXIT_FAILURE,
unistd.h提供
getopt()。
清单 4. 系统头文件
#include <stdio.h> #include <stdlib.h> #include <unistd.h> |
globalArgs结构,用于以合理的方式存储命令行选项。由于这是个全局变量,程序中任何位置的代码都可以访问这些变量,以确定是否创建关键字索引、生成何种语言等等事项。最好让
main()函数外的代码将此结构视为一个常量、只读存储区,因为程序的任何部分都可以依赖于其内容。
每个命令行选择都有一个对应的选项,而其他变量用于存储输出文件名、指向输入文件列表的指针和输入文件数量。
相关文章推荐
- 使用 getopt() 进行命令行处理,optind,optarg,optopt
- 使用 getopt() 进行命令行处理
- 使用 getopt() 进行命令行处理
- 使用 getopt() 进行命令行处理
- 使用 getopt() 进行命令行处理
- 使用 getopt() 进行命令行处理
- 使用 getopt() 进行命令行处理
- 使用 getopt() 进行命令行处理
- 使用 getopt() 进行命令行处理
- 使用 getopt() 进行命令行处理
- 使用 getopt() 进行命令行处理
- 使用 getopt() 进行命令行处理
- 使用 getopt() 、getopt_long()、getopt_long_only()进行命令行处理
- 使用 getopt() 进行命令行处理
- 使用 getopt() 进行命令行处理
- 使用 getopt() 、getopt_long()、getopt_long_only()进行命令行处理
- 使用 getopt() 进行命令行处理
- 使用 getopt() 进行命令行处理 ( 转 )
- 使用 getopt() 进行命令行处理
- 使用 getopt() 进行命令行处理