简体   繁体   English

如何为具有不同arguments的函数声明一个function指针数组?

[英]How to declare an array of function pointers for functions with different arguments?

I am writing some tests for my project, and the functions have the same return type but a different number of parameters.我正在为我的项目编写一些测试,这些函数具有相同的返回类型但参数数量不同。 I want to use an array of function pointers to call these test functions.我想使用一个 function 指针数组来调用这些测试函数。 How to declare an array of function pointers for such functions?如何为此类函数声明一个 function 指针数组?

The functions are declared as:函数声明为:

bool test1();
bool test2(char const *string, uint32_t length);

Consider that function pointers are not magic tricks, they still have to abide to the ABI calling convention, meaning that a function with a certain signature is intrinsically different from a function with a different signature.考虑到 function 指针不是魔术,它们仍然必须遵守 ABI 调用约定,这意味着具有特定签名的 function 与具有不同签名的 function 在本质上是不同的。

Using a function pointer is more of a way to have dynamic methods, than to achieve polymorphism. 使用 function 指针更像是一种拥有动态方法的方式, 而不是实现多态性。 EDIT: This is not polymorphism.编辑:这不是多态性。

However, you can accomplish somewhat you ask by replacing each of the test functions to accept a void* and then code your parameters in a struct.但是,您可以通过替换每个测试函数以接受void*然后在结构中编码您的参数来完成您的要求。

// Declare the test functions

//bool test1();
bool test1(void* struct_address)
{
    // struct address unused.
}

// Parameters for test2
struct test2{
    char const* string;
    uint32_t*   length;
}

//bool test2(char const *string, uint32_t length);
bool test2(void* struct_address)
{
    struct test2 test2_s = *(struct test2*)(struct_address);

    // Work with test2_s
}

// Declare the function pointer 
bool (*test_ptr)(void *);

// call test1
test_ptr = test1; test_ptr((void*)NULL);

// call test2
struct test2 test2_s = {param1,param2};
test_ptr = test2; test_ptr((void*)&test2_s);

Be careful because if you pass the wrong struct type you will get memory leaks and segmentation errors.要小心,因为如果你传递了错误的结构类型,你将得到 memory 泄漏和分段错误。 Since this is a test environment, however, this can be mitigated.但是,由于这是一个测试环境,因此可以缓解这种情况。

In C, an empty parameter list in a function declaration does not mean that the function takes no argument ;在 C 中,function声明中的空参数列表并不意味着 function没有参数 rather, it means that it takes an unspecified number of arguments .相反,这意味着它需要一个未指定的数字 arguments 1 1个

So, syntactically at least, you can specify an array of function pointers, each with an unspecified number of arguments (but a fixed return type), like this: bool (*FnPtrArray[100])();因此,至少在语法上,您可以指定一个由 function 个指针组成的数组,每个指针的编号都未指定为 arguments(但返回类型固定),如下所示: bool (*FnPtrArray[100])(); . . You can then assign, to different elements of such an array, addresses of functions with different argument types and numbers.然后,您可以为此类数组的不同元素分配具有不同参数类型和编号的函数地址。 However, there can then be no compile-time check that those functions are called correctly, or any implicit conversion of given argument types to the 'correct' forms.但是,这样就无法在编译时检查这些函数是否被正确调用,也无法将给定参数类型隐式转换为“正确的”forms。

The code below illustrates this (but note that I do not recommend using code like this , because of the inherent dangers that passing incorrect arguments can cause):下面的代码说明了这一点(但请注意,我不建议使用这样的代码,因为传递不正确的 arguments 可能会导致固有的危险):

#include <stdio.h>
#include <stdbool.h>

bool Foo(int a) {
    printf("Foo: %d ...\n", a);
    return a % 2;
}

bool Bar(double x, double y) {
    printf("Bar: %5.3lf %5.3lf...\n", x, y);
    return x < y;
}

int main()
{
    bool (*FnPtrArray[100])();

    // So we can't tell at compile time which elements point where ...
    printf("Enter a number: ");
    int n = 42;
    scanf("%d", &n);
    if (n % 2) {
        FnPtrArray[0] = Foo;
        FnPtrArray[1] = Bar;
    }
    else {
        FnPtrArray[1] = Foo;
        FnPtrArray[0] = Bar;
    }

    // Notes assuming given "n" is odd ...
    printf("%d\n\n", FnPtrArray[0](3));         // Works
    printf("%d\n\n", FnPtrArray[0](3.0));       // Wrong argument type
    printf("%d\n\n", FnPtrArray[1](1.0, 2.0));  // Works
    printf("%d\n\n", FnPtrArray[1](1, 2));      // Wrong argument types
    printf("%d\n\n", FnPtrArray[1](1.0));       // Wrong number of args

    return 0;
}

Here's a link to the above code on Compiler Explorer , for those who want to test with various compilers and settings.这是Compiler Explorer上上述代码的链接,供那些想要使用各种编译器和设置进行测试的人使用。


1 This is very different from C++, where an empty formal parameter list does mean no argument. 1这与 C++ 非常不同,其中空的形式参数列表并不意味着没有参数。

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

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