我有一个函数 foo(char *n, ...);
我需要获取并使用所有可选的 char
参数。
我有一个想法可以使用
while(va_arg(argPtr, char) != NULL)
{
...
}
了解我何时到达列表末尾。那么,它会起作用吗,如果在函数调用中我会做 foo(n, 't', 'm', '$', NULL);
?
NULL
会被 va_arg 读取为 char 吗?
或者也许有一种更常见的方法来确定列表的结尾,而无需添加 NULL
作为最后一个参数?
最佳答案
对于使用 va_arg
的函数,没有直接方法来确定给定调用传递的参数的数量或类型。
特别是您提出的方法:
while(va_arg(argPtr, char) != NULL)
不正确。 va_arg(argPtr, char)
产生一个 char
类型的值,而 NULL
是一个空指针常量。 (NULL
通常定义为 0
,比较等于空字符 '\0'
,但您不能依赖它。 )
任何可变参数函数都必须有一种方法供调用者指定参数的数量和类型。例如,*printf
函数通过(非可变参数)格式字符串执行此操作。 POSIX execl*()
函数需要一系列 char*
参数;参数列表的末尾由调用者用 (char*)NULL
标记。其他方法也是可能的,但它们几乎都依赖于运行时参数中给出的信息。 (您可以使用一些其他方法,例如全局变量。请不要。)
这会给调用者带来负担,以确保传递给函数的参数是一致的。函数本身无法确认这一点。不正确的调用,如 printf("%d\n", "hello")
或 execlp("name", "arg1")
有未定义的行为.
还有一件事:您不能将 va_arg
与 char
类型的参数一起使用。当您调用可变参数函数时,、...
对应的参数将被提升。类型小于 int
的整数参数被提升为 int
或 unsigned int
,类型为 float
的参数是提升为 double
。如果调用方传递类型为 char
的参数,则该函数必须调用 va_arg(argPtr, int)
。
(在您不太可能遇到的非常晦涩的情况下,char
可以提升为 unsigned int
。只有当纯 char
是无符号的并且 sizeof (int) == 1
,这意味着一个字节至少是 16 位。)
关于c - 如何确定 va_arg 列表的结尾?,我们在Stack Overflow上找到一个类似的问题: https://stackoverflow.com/questions/37356030/