繁体   English   中英

功能原型中的“......”

[英]“…” in function prototype

我看到有人的C ++代码有如下的函数声明:

void information_log( const char* fmt , ...)

或像块一样

catch(...)
{
}

这是什么意思?

省略号... ,在函数原型中,用于将函数表示为可变参数。 也就是说,它允许将可变数量的参数传递给函数。 在这种形式中,函数必须为用户定义一些方式来准确指定它们呈现的参数数量,因为C ++中的可变参数库函数无法动态地确定此信息。

例如,stdio函数printf是原型的一个这样的函数:

int printf(const char *format, ...);

据推测,根据两个原型之间的相似之处,您描述的information_log函数旨在反映printf的大部分功能,甚至可能在内部使用printf或其中一个表兄弟。

以下是如何实现可变参数函数的示例:

// cstdarg provides access to the arguments passed to the ellipsis
#include <cstdarg> // or (#include <stdarg.h>)
#include <cstdio>
#include <cstring>

// Concatenates as many strings as are present
void concatenate(char ** out, int num_str, ...)
{
    // Store where the arguments are in memory
    va_list args;

    // Find the first variadic argument, relative to the last named argument
    va_start(args, num_str);

    int out_len = 0;
    int * lengths = new int[num_str];
    char ** strings = new char*[num_str];

    // Extract the strings from the variadic argument list
    for(int i = 0; i < num_str; i++)
    {
        // Specify the position in the argument list and the type
        // Note: You must know the type, stdarg can't detect it for you
        strings[i] = va_arg(args, char *);
        lengths[i] = strlen(strings[i]);
        out_len += lengths[i];
    }

    // Concatenate the strings
    int dest_cursor = 0;
    (*out) = new char[out_len + 1];
    for(int i = 0; i < num_str; i++)
    {
        strncpy( (*out) + dest_cursor, strings[i], lengths[i]);
        dest_cursor += lengths[i];
    }
    (*out)[dest_cursor] = '\0';

    // Clean up
    delete [] strings;
    delete [] lengths;
    va_end(args);
}

int main()
{
    char * output = NULL;

    // Call our function and print the result
    concatenate(&output, 5, "The ", "quick", " brown ", "fox ", "jumps!\n");
    printf("%s", output);

    delete [] output;
    return 0;
}

这里真的是两个单独的问题,只是使用相同的符号。 :-)

原型只是表明可变数量的参数。 我真的可以说的是,它有点像C的printf函数,如果你碰巧知道的话。 该函数只是在需要时继续引入参数。

catch (...)代码只是意味着捕获任何异常。 (通常你把它放在一些特定的catch块之后,这样就可以作为“全能”了。)

对于一个捕获,它意味着捕获任何东西。 因此抛出的所有异常都将进入此catch块。

对于参数列表,它意味着存在可变数量的参数。 您必须使用stdarg.h API来解析它们。

$ 5.2.2 / 6 - “一个函数可以被声明为接受更少的参数(通过声明默认参数(8.3.6))或更多的参数(通过使用省略号,... 8.3.5)而不是参数的数量函数定义(8.4)。[注意:这意味着,除了使用省略号(...)之外,每个参数都有一个参数。]“

这很好地总结了OP中“information_log”声明的解释

$ 15.3 / 6 - “A ...在一个处理程序的异常声明函数中,与函数参数声明中的函数类似;它指定了任何异常的匹配。如果存在,...处理程序应该是它的最后一个处理程序试试阻止。“

虽然不是标准术语,但它通常被称为catch all子句或catch all handler。

void f(){
    try{
        throw 2.2;       // throw double
    }
    catch(int){}              // standard conversion from double to int not permitted
    catch(...){
        cout << "catch it here";   // is caught here in catch all clause
    }
}

int main(){
    f();
}

请参阅具有未指定参数数量的函数

使用省略号,...,使用C ++函数原型, 意味着可以使用未知数量和类型的参数指定函数 此功能可用于抑制参数类型检查,并允许灵活的功能接口。 C ++允许使用未指定数量的参数声明函数。

暂无
暂无

声明:本站的技术帖子网页,遵循CC BY-SA 4.0协议,如果您需要转载,请注明本站网址或者原文地址。任何问题请咨询:yoyou2525@163.com.

 
粤ICP备18138465号  © 2020-2024 STACKOOM.COM