2010-09-09 51 views
0

我想第一次使用getopt_long()函數,只有我遇到了非標誌參數的問題。例如,在我的代碼中,當給出未知參數時,我想將其用作輸入文件。當我只用一個文件名運行它時,它不會被打印,如果我第一次使用一個標誌,任何標誌,那麼我就可以打印它。getopt_long()和不是標誌的參數?

我該如何解決這個問題?

#include <stdio.h> 
#include <getopt.h> 

static struct option long_options[] = { 
    {"help", no_argument,  0, 'h'}, 
    {"input", required_argument, 0, 'i'}, 
    {"output", required_argument, 0, 'o'}, 
    {"algorithm", required_argument, 0, 'a'}, 
    {0, 0, 0, 0} 
}; 

int main(int argc, char *argv[]) { 
    int c; 
    int option_index = 0; 

    while(42) { 
    c = getopt_long(argc, argv, "hi:o:a:", long_options, 
    &option_index); 
    if(c == -1) 
    break; 

    switch(c) { 
    case 'h': /* --help */ 
    printf("--help flag\n"); 
    break; 
    case 'i': /* --input */ 
    printf("--input flag\n"); 
    break; 
    case 'o': /* --output */ 
    printf("--output flag\n"); 
    break; 
    case 'a': /* --algorithm */ 
    printf("--algorithm flag \n"); 
    break; 
    default: /* ??? */ 
    fprintf(stderr, "Invalid option"); 
    return 1; 
    } 

    if(optind < argc) { 
    printf("other arguments: "); 

    while(optind < argc) { 
    printf ("%s ", argv[optind]); 
    optind++; 
    } 

    printf("\n"); 
    } 
    } 

    return 0; 
} 

回答

5

該回路應該只包含開關。處理的殘留參數在一個單獨的(未嵌套的)循環:

#include <stdio.h> 
#include <getopt.h> 

static struct option long_options[] = 
{ 
    {"help", no_argument,  0, 'h'}, 
    {"input", required_argument, 0, 'i'}, 
    {"output", required_argument, 0, 'o'}, 
    {"algorithm", required_argument, 0, 'a'}, 
    {0, 0, 0, 0} 
}; 

int main(int argc, char *argv[]) 
{ 
    int opt; 
    int option_index = 0; 
    int i; 

    while ((opt = getopt_long(argc, argv, "hi:o:a:", long_options, &option_index)) != -1) 
    { 
     switch(opt) 
     { 
      case 'h': /* --help */ 
       printf("--help flag\n"); 
       break; 
      case 'i': /* --input */ 
       printf("--input flag (%s)\n", optarg); 
       break; 
      case 'o': /* --output */ 
       printf("--output flag (%s)\n", optarg); 
       break; 
      case 'a': /* --algorithm */ 
       printf("--algorithm flag (%s)\n", optarg); 
       break; 
      default: /* ??? */ 
       fprintf(stderr, "Invalid option %c\n", opt); 
       return 1; 
     } 
    } 

    for (i = optind; i < argc; i++) 
     printf("Process: %s\n", argv[i]); 

    return 0; 
} 

有一種方法以具有GNU getopt()getopt_long()返回文件名稱參數就好像它們是用「字母」選項^ A「\ 1」 ;使用'-'作爲短選項字符串的第一個字符,並在交換機中捕獲'\1'; optarg的值是該文件的名稱。

#include <stdio.h> 
#include <getopt.h> 

static struct option long_options[] = 
{ 
    {"help", no_argument,  0, 'h'}, 
    {"input", required_argument, 0, 'i'}, 
    {"output", required_argument, 0, 'o'}, 
    {"algorithm", required_argument, 0, 'a'}, 
    {0, 0, 0, 0} 
}; 

int main(int argc, char *argv[]) 
{ 
    int opt; 
    int option_index = 0; 
    int i; 

    while ((opt = getopt_long(argc, argv, "-hi:o:a:", long_options, &option_index)) != -1) 
    { 
     switch(opt) 
     { 
      case 'h': /* --help */ 
       printf("--help flag\n"); 
       break; 
      case 'i': /* --input */ 
       printf("--input flag (%s)\n", optarg); 
       break; 
      case 'o': /* --output */ 
       printf("--output flag (%s)\n", optarg); 
       break; 
      case 'a': /* --algorithm */ 
       printf("--algorithm flag (%s)\n", optarg); 
       break; 
      case '\1': 
       printf("File: %s\n", optarg); 
       break; 
      default: /* ??? */ 
       fprintf(stderr, "Invalid option %c\n", opt); 
       return 1; 
     } 
    } 

    for (i = optind; i < argc; i++) 
     printf("Process: %s\n", argv[i]); 

    return 0; 
} 

但是,你需要的參數處理後循環迴路的情況下,你的壞脾氣的用戶類型:

program -- abc def 

的「--」終止while()循環不處理文件名參數。

3

getopt_long返回-1(表示沒有更多選項)時,它不起作用,因爲您跳出外部while循環。

您需要將if (optind < argc)塊移出外部while環路;無論如何,它不屬於那裏。如果你將while環寫爲:

while ((c = getopt_long(...)) != -1) 
{ 
    switch (c) 
    { 
     /* Deal with flags. */ 
    } 
}