2023年7月28日,周五上午
这是我目前碰到过的比较复杂的函数之一,
为了彻底弄懂这个函数,我花了几个小时。
为了更好的说明这个函数,之后我可能会录制讲解视频并上传到B站,
如果我上传到B站,我会在文章添加视频链接的。
内容太多了,没写完,有空再更新......
函数原型
#include<unistd.h>int getopt(int argc,char * const argv[ ],const char * optstring);
- 参数
argc
:表示命令行参数的数量 - 参数
argv
:表示命令行参数的数组 - 参数
optstring
:表示可接受的选项字符串
4个辅助外部变量
与常见的库函数不同,getopt函数还带有4个外部变量作为辅助:
extern char *optarg;
extern int optind, opterr, optopt;
- 外部变量
optarg
:用于存储选项的参数值 - 外部变量
optind
:当前解析的选项在命令行参数数组中的索引 - 外部变量
opterr
:控制错误消息的输出 - 外部变量
optopt
:用于存储未识别的选项字符
返回值
以下关于getopt返回值的英文解释引自getopt
The getopt() function shall return the next option character specified on the command line.
A colon ( ':' ) shall be returned if getopt() detects a missing argument and the first character of optstring was a colon ( ':' ).
A question mark ( '?' ) shall be returned if getopt() encounters an option character not in optstring or detects a missing argument and the first character of optstring was not a colon ( ':' ).
Otherwise, getopt() shall return -1 when all command line options are parsed.
以下是我的翻译:
正确情况下,getopt函数应该返回命令行中的下一个选项字符的ASCII码。
如果optstring的第一个字符是冒号":",那么当要填写参数的选项没有填写参数时,返回冒号":"的ASCII码。
当opstring的第一个字符不是冒号":"时,如果getopt函数遇到了一个不在optstring中的选项或要填写参数的选项没有填写参数,那么就会返回问号"?"的ASCII码。
否则,getopt函数会在命令行的参数都已经被访问的时候返回-1.
现在看不懂不要紧,先继续往下看,理解了下面的知识才能更好的理解返回值。
optstring怎么写
概述与示例
getopt(int argc,char *argv[],"ab:c");//示例Agetopt(int argc,char *argv[],"ab::c");//示例Bgetopt(int argc,char *argv[],":abc");//示例C
示例A中的”ab:c“,意为有三个选项:a、b和c,其中选项b必须要填写参数
示例B中的"abc::",意为有三个选项:a、b和c,其中选项b可以填写参数,也可不填写参数
示例C中的”:abc“,意为有三个选项:a、b和c,开头是":"意味着改变返回值和输出错误的方式
第一个字符是不是冒号":"
在getopt中存在着两种错误:
- 必须添加参数的选项没有填写参数
- 写上了不存在于opstring中的选项
如果optstring的第一个字符是冒号":",那么意味着:
- 当必须添加参数的选项没有填写参数的时,只会返回冒号":"的ASCII码;
- 当写上了不存在于opstring中的选项时,只会返回问号"?"的ASCII码。
如果optstring的第一个字符不是冒号":",那么意味着:
- 当必须添加参数的选项没有填写参数的时,不仅会返回问号"?"的ASCII码,而且会在控制台输出一段提示缺少参数的报错信息;
- 当写上了不存在于opstring中的选项时,不仅会返回问号"?"的ASCII码,而且会在控制台输出一段提示无效选项的报错信息。
总而言之,
第一个字符是冒号":",不会在控制台输出相应的报错信息,且两种错误的返回值不同:一个是问号"?"的ASCII码,一个是冒号":"的ASCII码;
第一个字符不是冒号":",会在控制台输出相应的报错信息,且两种错误的返回值相同:都是问号"?"的ASCII码。
参考文章
Linux下getopt()函数的简单使用 - 青儿哥哥 - 博客园 (cnblogs.com)
(1条消息) 原来命令行参数处理可以这么写-getopt?_huangxiaohu_coder的博客-CSDN博客
getopt