getopt_long()解析命令行选项参数

本文详细介绍了getopt_long函数的功能及使用方法,包括如何解析命令行参数中的短选项和长选项,以及具体的代码示例。

摘要生成于 C知道 ,由 DeepSeek-R1 满血版支持, 前往体验 >

#include
函数说明:
函数getopt用来解析命令行参数。
函数getopt_long支持长选项的命令行解析。

函数原型:
int getopt_long(int argc, char* const argv[], 
                         const char *optstring,
                         const struct option *longopts, 
                         int *longindex);
参数:
argc、argv直接从main函数中获取。
opting是选项参数组成的字符串,由下列元素组成:
1.单个字符,表示选项,
2.单个字符后接一个冒号:表示该选项后必须跟一个参数。参数紧跟在选项后或者以空格隔开。该参数的指针赋给optarg。
3.单个字符后跟两个冒号,表示该选项后可以有参数也可以没有参数。如果有参数,参数必须紧跟在选项后不能以空格隔开。该参数的指针赋给optarg。(这个特性是GNU的扩张)。
optstring是一个字符串,表示可以接受的参数。例如,"a:b:cd",表示可以接受的参数是a,b,c,d,其中,a和b参数后面跟有更多的参数值。(例如:-a host -b name)
longopts是一个结构的实例
struct option
{
   const char *name; //name表示的是长参数名
   int has_arg; // has_arg有3个值,no_argument(或者是0),表示该参数后面不跟参数值
                 // required_argument(或者是1),表示该参数后面一定要跟个参数值
                 // optional_argument(或者是2),表示该参数后面可以跟,也可以不跟参数值
   int *flag;    // 用来决定getopt_long()的返回值是什么。
                 // flag是null,则函数会返回与该项option匹配的val值。
   int val;      // 和flag联合决定返回值
 };
=========================================================================
给个例子:
struct option long_options[] = {
            {"a123", required_argument, 0, 'a'},
            {"c123", no_argument, 0, 'c'},
};
现在,如果命令行的参数是-a 123,那么调用getopt_long()将返回字符'a',并且将字符串123由optarg返回(注意注意!字符串123由optarg带回!optarg不需要定义,在getopt.h中已经有定义)。
那么,如果命令行参数是-c,那么调用getopt_long()将返回字符'c',而此时,optarg是null。
最后,当getopt_long()将命令行所有参数全部解析完成后,返回-1。
===========================================================================
以上来自网络,便于学习记忆摘录在这里,下面是自己的理解:
函数原型:int getopt_long(int argc, char* const argv[], 
                         const char *optstring,
                         const struct option *longopts, 
                         int *longindex);
其中optstring为单个字符参数,称为short_opts。
而longopts为多个字符(即一个或多个单词连接)参数,称为long_opts。
参数longindex为longopts数组中的索引返回值。
具体用法参考suricata中main()函数中解析命令行参数:
// 短字符参数
char short_opts[] = "c:TDhi:l:q:d:r:us:S:U:VF:";

// 长字符参数
 struct option long_opts[] = {
        {"dump-config", 0, &dump_config, 1},
        {"pfring", optional_argument, 0, 0},
        {"pfring-int", required_argument, 0, 0},
        {"pfring-cluster-id", required_argument, 0, 0},
        {"pfring-cluster-type", required_argument, 0, 0},
        {"af-packet", optional_argument, 0, 0},
        {"pcap", optional_argument, 0, 0},
        {"pcap-buffer-size", required_argument, 0, 0},
        {"unittest-filter", required_argument, 0, 'U'},
        {"list-app-layer-protos", 0, &list_app_layer_protocols, 1},
        {"list-unittests", 0, &list_unittests, 1},
        {"list-cuda-cards", 0, &list_cuda_cards, 1},
        {"list-runmodes", 0, &list_runmodes, 1},
        {"list-keywords", optional_argument, &list_keywords, 1},
        {"runmode", required_argument, NULL, 0},
        {"engine-analysis", 0, &engine_analysis, 1},
        {"pidfile", required_argument, 0, 0},
        {"init-errors-fatal", 0, 0, 0},
        {"fatal-unittests", 0, 0, 0},
        {"user", required_argument, 0, 0},
        {"group", required_argument, 0, 0},
        {"erf-in", required_argument, 0, 0},
        {"dag", required_argument, 0, 0},
        {"napatech", 0, 0, 0},
        {"build-info", 0, &build_info, 1},
        {NULL, 0, NULL, 0}
    };
   // 长字符数组索引
    int option_index = 0;
 
 // 以下是用法 
 while ((opt = getopt_long(argc, argv, short_opts, long_opts, &option_index)) != -1) 
 {
        switch (opt) 
        {       // case为函数返回值
         case 0:
            if (strcmp((long_opts[option_index]).name , "pfring") == 0 ||                                        strcmp((long_opts[option_index]).name , "pfring-int") == 0) 
            {
               // TO-DO...
             }
             else if (strcmp((long_opts[option_index]).name , "pcap") == 0) 
             {
               // TO-DO...
             }
             break;
          case 'c':
             break; 
          case 'T':
             break;
          default:
             usage(argv[0]); 
             exit(EXIT_FAILURE);
        }
 }
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

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

抵扣说明:

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

余额充值