apue編程之getopt ,getopt_long使用方法以及實例

1. getopt

該函數用來解析命令行參數。git

1.1. 函數定義

int getopt(int argc, char * const argv[], const char *optstring);
#include <unistd.h>

前兩個參數設爲main函數的兩個參數。數據庫

optstring設爲由該命令要處理的各個選項組成的字符串。選項後面帶有冒號':'時,該選項是一個帶參數的選項。

舉例:make -f filename -n
-f 是一個帶參數的選項,-n 是一個沒有參數的選項。數組

能夠像下面這樣調用 函數getopt 來解析上面的例子。微信

c = getopt(argc, argv, "f:n");

此函數的返回值即爲當前找到的命令選項,所有選項都找到時的返回值爲-1app

一般一個命令有多個選項,爲了取得全部選項,須要循環調用此函數,直到返回值爲-1。
要使用此函數,還有幾個全局變量必需要了解:函數

extern char *optarg;
extern int optind, opterr, optopt;
 /*
optarg: 當前選項帶參數時,optarg指向該參數。
optind: argv的索引。一般選項參數取得完畢時,經過此變量能夠取得非選項參數(argv[optind])
optopt: 一個選項在argv中有,但在optstring中不存在時,或者一個帶參數的選項沒有參數時,
        getopt()返回'?',同時將optopt設爲該選項。
opterr: 將此變量設置爲0,能夠抑制getopt()輸出錯誤信息。
*/

1.2. 實例

#include <unistd.h>
#include <string.h>
#include <stdio.h>

int main(int argc, char *argv[ ])  
{
    int c;
    int flg = 0;
    char filename[256];
    char testdata[256];
   
    if (argc < 2)
    {
        printf("usage:%s [-f filename] [-n] testdata\n", argv[0]);
        return -1;
    } 
   
    opterr = 0;
    while ((c = getopt(argc, argv, "f:n")) != -1)
    {
        switch (c)
        {
            case 'f':
                strncpy(filename, optarg, sizeof(filename)-1);
                break;
            case 'n':
                flg = 1;
                break;
            case '?':
            default:
                printf("usage:%s [-f filename] [-n] testdata\n", argv[0]);
                return -1;
        } 
    } 
   
    if (argv[optind] == NULL)
    {
        printf("usage:%s [-f filename] [-n] testdata\n", argv[0]);
        return -1;
    } 
    else
    {
        strncpy(testdata, argv[optind], sizeof(testdata)-1);
    } 
   
    printf("fliename:%s flg:%d testdata:%s\n", filename, flg, testdata);
    return 0;
}

2. getopt_long

這是支持長命令選項的函數,長選項以'--'開頭。ui

2.1. 函數定義

int getopt_long(int argc, char * const argv[],
                  const char *optstring,
                  const struct option *longopts, int *longindex);
#include <getopt.h>

前三個參數與函數getopt的參數是同樣的。
只支持長選項時,參數optstring設置爲NULL或者空字符串""。
第四個參數是一個構造體struct option的數組。此構造體定義在頭文件getopt.h中。此數組的最後一個須將成員都置爲0。this

struct option {
const char *name;
int has_arg;
int *flag;
int val;
};

構造體各個成員的解釋以下:
name : 長選項的名字。
has_arg : no_argument或0表示此選項不帶參數,required_argument或1表示此選項帶參數,optional_argument或2表示是一個可選選項。
flag : 設置爲NULL時,getopt_long()返回val,設置爲NULL之外時,>getopt_long()返回0,且將*flag設爲val。
val : 返回值或者*flag的設定值。有些命令既支持長選項也支持短選項,能夠經過設定此值爲短選項實現。命令行

第五個參數是一個輸出參數,函數getopt_long()返回時,longindex的值是struct option數組的索引。code

關於返回值有如下幾種狀況:

識別爲短選項時,返回值爲該短選項。
識別爲長選項時,若是flag是NULL的狀況下,返回val,若是flag非NULL的狀況下,返回0。
全部選項解析結束時返回-1。
存在不能識別的選項或者帶參數選項的參數不存在時返回'?' 。

2.2. 實例

#include <stdio.h>     /* for printf */
#include <stdlib.h>    /* for exit */
#include <getopt.h>

int main(int argc, char **argv) 
{
   int c;
   int digit_optind = 0;
   int flag = 0;
   
   while (1) {
       int this_option_optind = optind ? optind : 1;
       int option_index = 0;
       static struct option long_options[] = {
           {"add",     required_argument, 0,  0 },
           {"append",  no_argument,       0,  0 },
           {"delete",  required_argument, 0,  0 },
           {"verbose", no_argument,       0,  0 },
           {"create",  required_argument, 0, 'c'},
           {"file",    required_argument, 0, 'f'},
           {0,         0,                 0,  0 }
       };
   
       c = getopt_long_only(argc, argv, "abc:d:f:012", long_options, &option_index);
       if (c == -1)
           break;
   
       switch (c) {
       case 0:
           printf("option %s", long_options[option_index].name);
           if (optarg)
               printf(" with arg %s", optarg);
           printf("\n");
           break;
   
       case '0':
       case '1':
       case '2':
           if (digit_optind != 0 && digit_optind != this_option_optind)
             printf("digits occur in two different argv-elements.\n");
           
           digit_optind = this_option_optind;
           printf("option %c\n", c);
           break;
       case 'a':
           printf("option a\n");
           break;
       case 'b':
           printf("option b\n");
           break;
       case 'c':
           printf("option c with value '%s'\n", optarg);
           break;
       case 'd':
           printf("option d with value '%s'\n", optarg);
           break;
        case 'f':
            printf("option f with value '%s'\n", optarg);
            break;
       case '?':
           break;
       default:
           printf("?? getopt returned character code 0%o ??\n", c);
       }
   }
   
   if (optind < argc) {
       printf("non-option ARGV-elements: ");
       while (optind < argc)
           printf("%s ", argv[optind++]);
       printf("\n");
   }
   
   exit(EXIT_SUCCESS);
}

歡迎關注個人微信公衆號【MySQL數據庫技術】。

相關文章
相關標籤/搜索