如果我定义了一个可变函数:
#include <stdio.h>
#include <stdarg.h>
int f(char*s,...)
{
va_list ap;
int i=0;
va_start(ap, s);
while(s)
{
printf("%s ", s);
i++;
s=va_arg(ap,char*);
}
va_end(ap);
return i;
}
int main()
{
return f("a","b",0);
}
gcc(linux x64)编译它,exe运行并打印“a b”。
是否需要像以下那样的演员:
return f("a","b",(char*)0)
在常见系统上?
答案 0 :(得分:6)
编译器无法自动提升variadic参数的指针,例如,当您要在printf
中打印指针时,必须将其强制转换为void *
:
printf("%p", (void *)ptr);
同样的规则适用于所有可变参数函数,编译器无法知道您的函数期望char *
,0默认情况下只是一个整数,所以是的,您需要将其(char *)0
。< / p>
即使NULL
也必须使用您的函数(char *)NULL
那么为什么main()会起作用,什么时候会失败呢?
你的代码并没有“真正起作用”。您的代码调用未定义的行为,任何事情都可能发生,因此没有人可以回答这个问题。在这里,你很幸运,但下次也许不是。
答案 1 :(得分:1)
您的代码应该在支持SYSV x64 ABI standard的任何系统上正常运行。它可能适用于使用具有类似要求的其他ABI标准的系统,并且可能在使用其他ABI 1 的任何系统上失败。根据C标准,这一切都是未定义的。
1 特别是,Microsoft不遵循标准的x64 ABI,它们有自己的标准。