24.6 getopt()、getopt_long()、getopt_long_only()是何用法
Q: 能给一个getopt()的例子吗
A: 小四 [email protected] 1999-04-05 17:02
/*
- For x86/Linux
- gcc -Wall -pipe -O3 -s -o getopt_test getopt_test.c */
#include <stdio.h> #include <stdlib.h> #include <strings.h> #include <string.h> #include <unistd.h>
#define VERSION "1.00 1999-04-05 17:02"
static void usage ( char arg ) { fprintf ( stderr, "Usage: %s [-h] [-v] [-i intvar] [-s strvar]\n", arg ); exit( EXIT_FAILURE ); } / end of usage */
int main ( int argc, char * argv[] ) { int ret = EXIT_FAILURE; int c; unsigned int intvar = 0; char *strvar = NULL;
if ( 1 == argc )
{
usage( argv[0] );
}
/*
* don't want getopt() writing to stderr
*/
opterr = 0;
/*
* getopt()第三形参最前面如果有冒号,就不会出现illegal option错误信息。
* 不过,如果指定了"opterr = 0",有无这个前导冒号都无所谓了。
*/
while ( EOF != ( c = getopt( argc, argv, ":hi:s:v" ) ) )
{
switch ( c )
{
case 'i':
intvar = ( unsigned int )strtoul( optarg, NULL, 0 );
break;
case 's':
strvar = optarg;
break;
case 'v':
printf( "%s ver "VERSION"\n", argv[0] );
return( EXIT_SUCCESS );
case 'h':
case '?':
default :
usage( argv[0] );
break;
} /* end of switch */
} /* end of while */
argc -= optind;
argv += optind;
printf
(
"intvar = %u\n"
"strvar = %s\n",
intvar,
NULL == strvar ? "(null)" : strvar
);
ret = EXIT_SUCCESS;
return( ret );
} /* end of main */
#if 0
$ ./getopt_test -h Usage: ./getopt_test [-h] [-v] [-i intvar] [-s strvar] $ ./getopt_test -i 1314 -s scz intvar = 1314 strvar = scz $ ./getopt_test -v ./getopt_test ver 1.00 1999-04-05 17:02
Q: 现在会用getopt()了,但如何支持"--parami intvar --params strvar"呢
A: 小四 [email protected] 2001-12-17 15:30
这需要用到getopt_long(),但这不是一个具有良好可移植性的函数。
/*
- For x86/Linux
- gcc -Wall -pipe -O3 -s -o getopt_long_test getopt_long_test.c */
#include <stdio.h> #include <stdlib.h> #include <strings.h> #include <string.h> #include <unistd.h> /*
- 为了使用getopt_long(),必须有如下两行内容 */ #define _GNU_SOURCE #include <getopt.h>
#define VERSION "1.00 2001-12-17 15:30" /*
- 不要与短选项所用的字符相同! / #define LONGOPTIONCHAR ''
static void usage ( char arg ) { fprintf ( stderr, "Usage: %s [-h] [--ver] [--parami intvar] [-params strvar]\n", arg ); exit( EXIT_FAILURE ); } / end of usage */
int main ( int argc, char * argv[] ) { int ret = EXIT_FAILURE; int c; unsigned int intvar = 0; char *strvar = NULL; struct option longOption[] = { { "ver", 0, NULL, LONGOPTIONCHAR }, { "parami", 1, NULL, LONGOPTIONCHAR }, { "params", 1, NULL, LONGOPTIONCHAR }, { NULL, 0, NULL, 0 } }; int longOptionIndex = 0;
if ( 1 == argc )
{
usage( argv[0] );
}
/*
* don't want getopt() writing to stderr
*/
opterr = 0;
while ( EOF != ( c = getopt_long( argc, argv, ":h", longOption, &longOptionIndex ) ) )
{
switch ( c )
{
case LONGOPTIONCHAR:
if ( optarg )
{
switch ( longOptionIndex )
{
case 1:
intvar = ( unsigned int )strtoul( optarg, NULL, 0 );
break;
case 2:
strvar = optarg;
break;
default:
break;
} /* end of switch */
}
else
{
switch ( longOptionIndex )
{
/*
* longOption[]的下标
*/
case 0:
printf( "%s ver "VERSION"\n", argv[0] );
return( EXIT_SUCCESS );
default:
break;
} /* end of switch */
}
break;
case 'h':
case '?':
default :
usage( argv[0] );
break;
} /* end of switch */
} /* end of while */
argc -= optind;
argv += optind;
printf
(
"intvar = %u\n"
"strvar = %s\n",
intvar,
NULL == strvar ? "(null)" : strvar
);
ret = EXIT_SUCCESS;
return( ret );
} /* end of main */
#if 0
$ ./getopt_long_test -h Usage: ./getopt_long_test [-h] [--ver] [--parami intvar] [-params strvar] $ ./getopt_long_test --parami 1314 --params scz intvar = 1314 strvar = scz $ ./getopt_long_test --ver ./getopt_long_test ver 1.00 2001-12-17 15:30
Q: 那getopt_long_only()与getopt_long()的区别是什么
A: 小四 [email protected] 2005-05-09 10:48
getopt_long_only()的行为与getopt_long()非常类似,但不限于用'--'引入长选项, '-'亦可引入长选项。当'-'引入的选项不匹配任何长选项时,继续进行短选项匹配。
再次提醒,getopt_long_only()与getopt_long()一样,不具有良好可移植性。
/*
- For x86/Linux
- gcc -Wall -pipe -O3 -s -o getopt_long_only_test getopt_long_only_test.c */
#include <stdio.h> #include <stdlib.h> #include <strings.h> #include <string.h> #include <unistd.h> /*
- 为了使用getopt_long_only(),必须有如下两行内容 */ #define _GNU_SOURCE #include <getopt.h>
#define VERSION "1.00 2005-05-09 10:48" /*
- 不要与短选项所用的字符相同!这次用空格符,更可靠些。 */ #define LONGOPTIONCHAR ' '
static void usage ( char arg ) { fprintf ( stderr, "Usage: %s [-h] [--v] [-i intvar] [--s strvar]\n", arg ); exit( EXIT_FAILURE ); } / end of usage */
int main ( int argc, char * argv[] ) { int ret = EXIT_FAILURE; int c; unsigned int intvar = 0; char *strvar = NULL; struct option longOption[] = { { "v", 0, NULL, LONGOPTIONCHAR }, { "s", 1, NULL, LONGOPTIONCHAR }, { NULL, 0, NULL, 0 } }; int longOptionIndex = 0;
if ( 1 == argc )
{
usage( argv[0] );
}
/*
* don't want getopt() writing to stderr
*/
opterr = 0;
while ( EOF != ( c = getopt_long_only( argc, argv, ":hi:", longOption, &longOptionIndex ) ) )
{
switch ( c )
{
case LONGOPTIONCHAR:
if ( optarg )
{
switch ( longOptionIndex )
{
case 1:
strvar = optarg;
break;
default:
break;
} /* end of switch */
}
else
{
switch ( longOptionIndex )
{
/*
* longOption[]的下标
*/
case 0:
printf( "%s ver "VERSION"\n", argv[0] );
return( EXIT_SUCCESS );
default:
break;
} /* end of switch */
}
break;
case 'i':
intvar = ( unsigned int )strtoul( optarg, NULL, 0 );
break;
case 'h':
case '?':
default :
usage( argv[0] );
break;
} /* end of switch */
} /* end of while */
argc -= optind;
argv += optind;
printf
(
"intvar = %u\n"
"strvar = %s\n",
intvar,
NULL == strvar ? "(null)" : strvar
);
ret = EXIT_SUCCESS;
return( ret );
} /* end of main */
#if 0
$ ./getopt_long_only_test -h Usage: ./getopt_long_only_test [-h] [--v] [-i intvar] [--s strvar] $ ./getopt_long_only_test --v ./getopt_long_only_test ver 1.00 2005-05-09 10:48 $ ./getopt_long_only_test -v ./getopt_long_only_test ver 1.00 2005-05-09 10:48 $ ./getopt_long_only_test -i 1314 -s scz intvar = 1314 strvar = scz