21

我有一个可变参数函数,它接受一个浮点参数。为什么它不起作用?

va_arg(arg, float)
4

2 回答 2

49

对应的函数的参数在传递给您的可变参数函数之前...提升。charshort被提升为int,float被提升为double, 等等

6.5.2.2.7 函数原型声明器中的省略号会导致参数类型转换在最后声明的参数之后停止。默认参数提升是在尾随参数上执行的。

原因是早期版本的 C 没有函数原型。参数类型在函数站点声明,但在调用站点不知道。但是不同类型的表示方式不同,传递参数的表示方式必须符合被调用函数的期望。因此 char 和 short 值可以传递给带有 int 参数的函数,或者可以将 float 值传递给带有 double 参数的函数,编译器将较小的类型“提升”为较大的类型。当在调用站点不知道参数的类型时,仍然会看到这种行为——即,对于可变参数函数或没有原型声明的函数(例如,int foo();)。

于 2012-06-30T00:49:50.690 回答
10

正如@dasblinkenlight 所提到的,float 被提升为 double。这对我来说可以:

#include <stdio.h>          
#include <stdarg.h>

void foo(int n, ...)
{   
    va_list vl;
    va_start(vl, n);

    int c; 
    double val; 

    for(c = 0; c < n; c++) {
        val = va_arg(vl, double);
        printf("%f\n", val);
    }

    va_end(vl);
}


int main(void)
{
  foo(2, 3.3f, 4.4f);
  return 0;
}

输出:

3.300000
4.400000
于 2012-06-30T00:54:29.040 回答