【问题标题】:What's the meaning of the `...` parameter in a C function parameter list [duplicate]C函数参数列表中的`...`参数是什么意思[重复]
【发布时间】:2012-12-12 12:21:55
【问题描述】:

可能重复:
C/C++: Passing variable number of arguments around

按函数声明方式

return-type function-name(parameter-list, ...) {body ...}

下面的代码是不是一种重载?

(在 A_FILE.h 中)

typedef VOID *FUNCTION(UINTN Number, ...);

看来我可以只传递一个Number 参数,或者多个参数到FUNCTION 函数中,那么参数的数量取决于函数实现吗?

【问题讨论】:

标签: c function-parameter


【解决方案1】:

函数声明中的省略号意味着它将接受许多参数,否则,在运行时未知的可变参数,通过使用标准头文件stdarg.h,分别该头文件“stdarg.h”中的函数可以确定构成传递给函数的参数的每个可变参数是什么。

考虑这个代码示例:

#define PANIC_BUF_LEN 256
void panic(const char *fmt, ...){
    char buf[PANIC_BUF_LEN];
    va_list argptr;
    va_start(argptr, fmt);
    vsprintf(buf, fmt, argptr);
    va_end(argptr);
    fprintf(stderr, buf);
    exit(errcode);
}

典型的调用可以是示例之一:

panic("Error: %s failed! Due to unknown error, message is '%s'\n", "my_function", "Disk not ready");

将以这种方式在控制台上产生输出:

Error: my_function failed! Due to unknown error, message is 'Disk not ready'

注意函数va_start(...)va_end(...) 的用法,更不用说vsprintf(...) 将负责填充“未知”参数中的空白提供 va_list 是初始化为指向变量参数,这些参数在运行时是未知的

编辑:只是强调一下,调用假定C字符串格式形式的字符串参数小于PANIC_BUF_LEN表示的最大大小上面的示例,挑剔的不谈,这是为了说明一个函数如何接受许多使用的标准C格式字符串,例如,可以在字符串格式中指定%d,并且期望 int 匹配参数。

【讨论】:

    【解决方案2】:

    没有。 “...”表示可变参数。

    重载是指编译器混合名称以生成具有不同参数集的多个函数。在 C 中,函数名称不会混合,但函数可以接受 1 个或多个参数。

    【讨论】:

      【解决方案3】:

      它不是 C++ 意义上的重载,但它可以用于类似的效果。 ... 表示该函数在命名参数之后接受任意数量的附加参数(必须至少有一个命名参数),并且附加参数可以具有任何类型(有点)。 1 此类函数的实现必须能够在运行时推断其附加参数的数量和类型。例如,printf 可以打印任何内置类型,一次可以打印任意数量的内容,但您必须以与实际参数对应的格式字符串为它提供% 代码。

      用于模拟 C++ 风格重载的变量参数的一个值得注意的例子是 open 系统调用,在 C++ 术语中它有两个重载:

      int open(const char *pathname, int flags);
      int open(const char *pathname, int flags, mode_t mode);
      

      手册页是这样写的,但是如果你查看<fcntl.h>,你会发现实际的声明是

      int open(const char *, int, ...);
      

      如果在标志中设置了O_CREAT 位,则该实现仅查看第三个参数,并且据记录,如果您设置了该位,您必须提供第三个参数。与 C 中的往常一样,如果你做错了,编译器会高兴地看着它在运行时对你造成影响。

      1 多亏了一种名为“default argument promotion”的残留语言功能,当作为附加参数传递给采用可变数量参数的函数时,一些数字类型会变成其他更大的数字类型.只有在编写此类函数的主体时,您才需要担心这一点。

      【讨论】:

        猜你喜欢
        • 1970-01-01
        • 1970-01-01
        • 1970-01-01
        • 2013-08-12
        • 1970-01-01
        • 2013-11-08
        • 1970-01-01
        • 2019-06-22
        • 1970-01-01
        相关资源
        最近更新 更多