红联Linux门户
Linux帮助

C语言中可变参数的用法与实例

发布时间:2006-08-22 09:07:05来源:红联作者:hfh08
Syntax:
#include
type va_arg( va_list argptr, type );
void va_end( va_list argptr );
void va_start( va_list argptr, last_parm );

The va_arg() macros are used to pass a variable number of arguments to a function.

First, you must have a call to va_start() passing a valid va_list and the mandatory first argument of the function. This first argument can be anything; one way to use it is to have it be an integer describing the number of parameters being passed.
Next, you call va_arg() passing the va_list and the type of the argument to be returned. The return value of va_arg() is the current parameter.
Repeat calls to va_arg() for however many arguments you have.
Finally, a call to va_end() passing the va_list is necessary for proper cleanup.
For example:

int sum( int num, ... ) {
int answer = 0;
va_list argptr;

va_start( argptr, num );

for( ; num > 0; num-- ) {
answer += va_arg( argptr, int );
}

va_end( argptr );

return( answer );
}


int main( void ) {

int answer = sum( 4, 4, 3, 2, 1 );
printf( "The answer is %d\n", answer );

return( 0 );
}

This code displays 10, which is 4+3+2+1.

Here is another example of variable argument function, which is a simple printing function:

void my_printf( char *format, ... ) {
va_list argptr;

va_start( argptr, format );

while( *format != '\0' ) {
// string
if( *format == 's' ) {
char* s = va_arg( argptr, char * );
printf( "Printing a string: %s\n", s );
}
// character
else if( *format == 'c' ) {
char c = (char) va_arg( argptr, int );
printf( "Printing a character: %c\n", c );
break;
}
// integer
else if( *format == 'd' ) {
int d = va_arg( argptr, int );
printf( "Printing an integer: %d\n", d );
}

*format++;
}

va_end( argptr );
}


int main( void ) {

my_printf( "sdc", "This is a string", 29, 'X' );

return( 0 );
}

This code displays the following output when run:

Printing a string: This is a string
Printing an integer: 29
Printing a character: X



//一个实例
程序要求:
做一个LOG函数

log_printfbuf(char *fmt, ...)

打印出printf所相同的东西,然后再打印出多余的2个参数的buffer内容。
多余的参数第一个是buffer, 第二个是要打印的字节数目。


比如调用

char buf[256];

buf[0] = 0;
buf[1] = 0;
buf[2] = 1;
strcpy(buf+3, "ABCDSKKKKLKKKKASKK");
log_printfbuf("buffer at %p size %d:", buf, sizeof(buf), buf, 56);

会打印出
buffer at 08001000 size 256: {00}{00}{01}ABCASKKKLKKLWIKKKK....

这是根据一个实际需求而来的。可能有一点用途。
程序实现:
#include
#include
#include

void foo(char *fmt, ...);
void show_hex(char *s , int d);
void main()
{
char buf[256]={0};
buf[0] = 0;
buf[1] = 0;
buf[2] = 1;
strcpy(buf+3, "ABCDSKKKKKLLLLKKKASKK");

foo("buffer at %p size %d:", buf, sizeof(buf), buf, 56);

}
void foo(char *fmt, ...) {
va_list ap;
int d;
char c, *s;
va_start(ap, fmt);
while (*fmt)
{
if (*fmt =='%')
{

switch(*(++fmt)) {
case 's': /* string */
s = va_arg(ap, char *);
printf("%s", s);


break;
case 'p':
s = va_arg(ap, char *);
printf("%04X", (int)s);
break;
case 'd': /* int */
d = va_arg(ap, int);
printf("%d", d);

break;


case 'c': /* char */
/* need a cast here since va_arg only
takes fully promoted types */
c = (char) va_arg(ap, int);
printf("%c", c);

break;
}
}
else
printf( "%c", *fmt);

fmt++;

}
s = va_arg(ap, char *);
d = va_arg(ap, int);
show_hex(s,d);

va_end(ap);
}
void show_hex(char *s , int d)
{
for (int i =0 ; i< d ; i++)
{
printf("{%02X} ", (unsigned char)*(s+i));

}
printf("\n");
}
文章评论

共有 0 条评论