函数getopt(),及其参数optind

Linux中getopt函数、optind等变量使用详解 最近在学习《Unix网络编程》vol2时,发现书中例子经常使用一个命令行解析getopt函数,因为。该函数是由Unix标准库提供的函数,查看命令。,根据自己摸索,遂总结出使用方法。 阅读详情

getopt被用来解析命令行选项参数。

#include<unistd.h>
      extern char*optarg;  //选项的参数指针
      extern int optind,  //下一次调用getopt的时,从optind存储的位置处重新开始检查选项。 
      extern intopterr,  //当opterr=0时,getopt不向stderr输出错误信息。
      extern intoptopt;  //当命令行选项字符不包括在optstring中或者选项缺少必要的参数时,该选项存储在optopt中,getopt返回'?’、

      int getopt(int argc, char * const argv[], const char*optstring);
 调用一次,返回一个选项。在命令行选项参数再也检查不到optstring中包含的选项时,返回-1,同时optind储存第一个不包含选项的命令行参数。

首先说一下什么是选项,什么是参数。

1.单个字符,表示选项,

2.单个字符后接一个冒号:表示该选项后必须跟一个参数。参数紧跟在选项后或者以空格隔开。该参数的指针赋给optarg。
3单个字符后跟两个冒号,表示该选项后必须跟一个参数。参数必须紧跟在选项后不能以空格隔开。该参数的指针赋给optarg。(这个特性是GNU的扩张)。

例如gcc -g -o test test.c,其中g和o表示选项,test为选项o的参数。


上面是getopt()函数的基本含义,大家懂得了这些之后,我们一个例子加深一下理解。

例如我们这样调用getopt(argc, argv,"ab:c:de::");
从上面我们可以知道,选项a,d没有参数,选项b,c有一个参数,选项e有有一个参数且必须紧跟在选项后不能以空格隔开。getopt首先扫描argv[1]到argv[argc-1],并将选项及参数依次放到argv数组的最左边,非选项参数依次放到argv的最后边。
执行程序为:
     0     1   2   3  4   5    6  7   8   9 
$ ./test file1-a  -b -c code -d file2 -e file3
 扫描过程中,optind是下一个选项的索引,非选项参数将跳过,同时optind增1。optind初始值为1。当扫描argv[1]时,为非选项参数,跳过,optind=2;扫描到-a选项时,下一个将要扫描的选项是-b,则optind更改为3;扫描到-b选项时,后面有参数(会认为-c为选项b的参数),optind=5,扫描到code非选项跳过optind=6;扫描到-d选项,后面没有参数,optind=7;扫描到file2非选项跳过optind=8;扫描到-e后面本来应该有参数,optind=9但是有空格所以e的参数为空。
 
扫描结束后,getopt会将argv数组修改成下面的形式
      0    1   2  3  4   5  6       7     8     9
$ ./test  -a -b  -c  -d -e  file1  code file2  file3
 
同时,optind会指向非选项的第一个参数,如上面,optind将指向file1
代码如下:
#include<unistd.h>
#include<stdio.h>
int main(int argc, char *argv[])
{
   int aflag=0, bflag=0, cflag=0;
   int ch;
printf("optind:%d,opterr:%dn",optind,opterr);
printf("--------------------------n");
   while ((ch = getopt(argc, argv, "ab:c:de::")) !=-1)
   {
       printf("optind: %d,argc:%d,argv[%d]:%sn",optind,argc,optind,argv[optind]);
       switch (ch) {
       case 'a':
           printf("HAVE option: -ann");
    
           break;
       case 'b':
           printf("HAVE option: -bn");
         
           printf("The argument of -b is %snn", optarg);
           break;
       case 'c':
           printf("HAVE option: -cn");
           printf("The argument of -c is %snn", optarg);

           break;
   case 'd':
       printf("HAVEoption: -dn");
      break;
   case 'e':
       printf("HAVEoption: -en");
       printf("Theargument of -e is %snn", optarg);
      break;

       case '?':
           printf("Unknown option: %cn",(char)optopt);
           break;
       }
   }
   printf("----------------------------n");
   printf("optind=%d,argv[%d]=%sn",optind,optind,argv[optind]);
}
执行结果:
shiqi@wjl-desktop:~/code$vim getopt.c
shiqi@wjl-desktop:~/code$gcc getopt.c -o g
shiqi@wjl-desktop:~/code$./g file1 -a  -b -c code -d file2 -efile3
optind:1,opterr:1
--------------------------
optind:3,argc:10,argv[3]:-b
HAVE option:-a

optind:5,argc:10,argv[5]:code
HAVE option:-b
The argument of -b is-c

optind:7,argc:10,argv[7]:file2
HAVE option:-d

optind:9,argc:10,argv[9]:file3
HAVE option:-e
The argument of -e is(null)   

----------------------------

optind=6,argv[6]=file1        //while循环执行完后,optind=6



转载补充:==========================================

黄色部分,个人理解:

getopt首先扫描argv[1]到argv[argc-1],并将选项及参数依次放到argv数组的最左边,非选项参数依次放到argv的最后边。

执行程序为:
     0        1      2    3     4       5       6       7     8       9 
$ ./test  file1   -a   -b    -c    code   -d    file2    -e    file3
 
扫描结束后,getopt会将argv数组修改成下面的形式
      0      1   2   3   4   5   6       7        8     9
$ ./test  -a  -b  -c   -d   -e  file1  code file2  file3

应该是为optind保存了一个数组:a[]={0,2,3,4,6,8,1,5,7,9},对应上面的各个参数,而没有真正改变argv数组的顺序。

还有, extern int optind,  //下一次调用getopt的时,从optind存储的位置处重新开始检查选项。

当while循环结束时,如果还有剩余的参数,optind将指向第一个剩余参数,如例,最后optind=6,argv[6]=file1        //while循环执行完后,optind=6

如果,没有剩余参数,argv[optind]将是最后一个调用的参数。

所以,可以在while后面用 if(optind == argc)来检测是否缺少参数。当没有多余参数时,optind应该是argc-1的,即最后一个参数的位置。


补充部分纯属个人见解,如有错误请评论探讨,谢谢!


实战指南 | Adjust 与 Facebook、Google Ads 自归因配置全流程解析 本文详细解析了Adjust与Facebook、Google Ads自归因配置的全流程,帮助移动应用出海推广者解决广告归因难题。通过自归因功能(SAN),开发者可以获取更准确的数据、简化配置流程并扩大安装来源覆盖,显著提升广告效果监测和ROI计算效率。 阅读详情

相关推荐

海康摄像头V3.4 升级改造VUE3

摘要:本文介绍了一个基于Vue3的海康威视摄像头组件封装方案。针对官方仅提供HTML版本SDK的问题,作者通过封装实现了Vue3组件化集成,解决了iframe/webview引入方式的弊端。组件核心功能包括实时预览、本地录像、录像下载、截图抓拍等,并优化了SDK初始化逻辑(单例模式)、定位问题修复和错误处理机制。关键技术点包括:1)SDK插件容器定位修复;2)录像下载进度监控;3)多格式图片数据处理;4)多窗口场景下的SDK实例管理。该组件可直接通过npm安装使用,提供了完善的API和事件接口,显著提升了海

LINLINLINShi的博客 114

linux——getopt()和getopt_long()函数及optarg,optind, opterr, optopt全局变量

getopt() 函数 getopt() 头文件 #include&lt;unistd.h&gt; 定义函数 int getopt(int argc,char * const argv[ ],const char * optstring); extern char *optarg; extern int optind, opterr, optopt; getopt() 所设置的全局变量包括: o...

夜风的博客 1万+

【08】C#实战篇——C#调用C++ 动态库dll,报错 “无法加载DLL“xxx.dll”: 找不到指定的模块。 (异常来自 HRESULT:0x8007007E)。”

摘要: 本文详细分析了C#调用C++封装的DLL时出现“无法加载DLL”错误的排查与解决方法。通过案例演示,列举了常见原因(如平台不匹配、路径错误、依赖缺失等),并重点介绍了使用VS的dumpbin工具检测DLL依赖项的方法。最终定位问题为缺失依赖的LineApi.dll和opencv_world455d.dll,将其放入C#的exe目录后解决。文章还对比了C++与C#的报错差异,提供了通用解决方案,包括检查运行时库、环境变量等,帮助开发者高效解决类似问题。 关键词: C#调用C++ DLL、dumpbin

程序员,他们想的是什么?他们想的永远都是技术,他们崇尚的也永远都是技术。 2099

c语言中的getopt()、optind的使用

根据《Head First C》P152例子改编 结论: getopt()会在最后一次执行时将argv变量进行排序,将参数(“d:t”)中提到的变量排序到最前面。这样后面的argc、argv变量通过optind计算就会非常清楚,经过遍历getopt()之后的参数就是没有被指定顺序的。 #include #include void print_arg(int argc,

x_think的专栏 2099

基于图像分割的LIDC-IDRI 数据集预处理之数据下载篇

近期接触到了一个关于图像分割实验项目,关于数据预处理部分在此予以记录,和大家分享。

qq_67696694的博客 1904

VAY 是 SAP 自动科目确定(OBYC-GBB)中的科目修改码,专用于带科目分配对象的销售订单发货场景,核心是触发 “Dr 成本要素科目(如销售费用 / 特定成本对象) Cr 库存商品” 的分录,

摘要:VAY是SAP中用于带科目分配对象(如成本中心、WBS)的销售订单发货的科目修改码,与标准VAX场景不同,它生成"借成本要素科目/贷库存商品"的分录。配置路径为OBYC-GBB-VAY,需确保借方科目为成本要素。典型业务场景包括免费样品、项目专用发货等。常见问题包括VAY未触发或科目记账错误,需检查销售订单科目分配、移动类型设置及OBYC配置。特殊场景建议单独配置科目以便费用分析。

金牌架构师 1257

[转]函数getopt(),及其参数optind

getopt被用来解析命令行选项参数。 #include <unistd.h>extern char *optarg;//选项的参数指针extern int optind, //下一次调用getopt的时,从optind存储的位置处重新开始检查选项。extern int opterr,//当opterr=0时,geto...

ditun4266的博客 114

Codex 实战 Skills:用 Skill 自动识别并提取 PDF/图片表格数据,效率提升 10 倍

本文介绍如何构建一个多模态文件解析 Skill,用于自动识别和提取 PDF/图片中的表格数据,提升 AI 智能体处理非结构化文档的效率。文章分析了传统方法的局限性,提出分层解析架构(预处理、检测、提取推理、后处理),推荐技术栈包括 pdfplumber、OpenCV 和多模态大模型。详细说明了 Skill 的元数据定义、数据模型设计(使用 Pydantic)和核心实现流程,通过混合策略实现从复杂文档到结构化 JSON/Markdown 的转换,使 AI 代理具备"阅读"多模态文档的能力。

yueyeguzhuo的专栏 308

[转载][总结]函数getopt(),getopt_long及其参数optind

看webbench源码的时候碰到命令行解析工具getopt的使用,虽然之前也看过一点,但都不是很全面,只是了解个大概,下面稍微总结一下: getopt和optind: getopt被用来解析命令行选项参数。 #include <unistd.h>extern char *optarg;//选项的参数指针extern int optind...

weixin_30435261的博客 225

Autosar 下电过程-基于ETAS工具

本文介绍基于ETAS工具对应的BIP包的下电过程,仅供参考。在最后调用SBC下电时,需要理清楚SBC的休眠流程,否则可能会出现休眠又唤醒情况。后面有空会介绍9471的休眠流程。

赞的博客 814

【2026OD新机考】【哈希表】20260422-文章特征提取【Py/Java/C++/C/JS/Go六种语言OD真题】【欧弟算法】全网注释最详细分类最全的华子OD真题题解

90+天陪伴式学习,100+直播课时,300+动画图解视频,500+LeetCode经典题,500+华为OD真题/大厂真题,还有简历修改、模拟面试、陪伴小群、资深HR对接将为你解锁。这道题的本质是多集合交集问题的变形,属于非常典型的哈希表应用题。,储存全局的每个片段中,各个字符最少出现的次数。表示该字母并非所有片段的公共字母。,按照顺序构建答案即可。没有字母在所有三个字符串中都出现。每个字母在各字符串中都至少出现。次,所以结果中每个字母出现一次。这样,当上述循环结束后,最终。显然在上述代码中,如果字母。

weixin_48157259的博客 66

IP5306轻载休眠导致设备假死?实战排查与解决指南

在便携设备和IoT硬件开发中,电源管理芯片是决定系统稳定性的关键一环。这类芯片往往集成了充电、升压、电量显示等复杂功能,但内部固化的自动检测逻辑也可能成为隐患。例如,当负载电流低于轻载判定阈值时,芯片可能误判为“空载”并自动休眠,导致设备放一晚上后无法唤醒,只能插充电器“复活”。理解轻载休眠原理与芯片保护机制,是解决此类问题的核心。通过寄存器配置、周期性唤醒或硬件EN控制等手法,工程师既能保留低功耗优势,又能避免设备陷入假死状态。本文结合IP5306的实际案例,从现象定位、参数实测到布局避坑,为电池供电产品

weixin_34380948的博客 332

Python 爬虫进阶:淘宝热卖商品价格走势抓取、反爬与分析全流程

在大数据时代,数据是商业决策的重要依据。电商平台上的商品价格走势,对于商家调整经营策略、消费者选择购买时机都有着关键的参考价值。本篇文章将深入解析如何利用 Python 爬虫抓取淘宝热卖商品的价格走势数据,并应对其中的反爬机制,最后对数据进行分析,带领大家领略 Python 爬虫在电商领域的强大应用。

yansideyucsdn的博客 1060
上一篇: linux终端中输出彩色字体
下一篇: Linux命令之for - Bash中的For循环
AstrayLinux
博客等级 码龄15年 55粉丝 38原创
评论
成就一亿技术人!
拼手气红包6.0元
还能输入1000个字符
 
 条评论被折叠 查看
添加红包

请填写红包祝福语或标题

个

红包个数最小为10个

元

红包金额最低5元

当前余额3.43元 前往充值 >
需支付:10.00元
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付元
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值