如何使用函数指针返回函数指针?

时间:2013-08-12 00:13:42

标签: c pointers

我正在研究unix中的信号处理并遇到了这个

void (*signal(int sig, void (*func)(int)))(int);

我不理解这个原型以及它如何返回指向函数的指针。

我也读到了这个答案: How do function pointers in C work?但我不清楚。

它应该返回一个函数指针,但我不明白它将返回类型指定为另一个函数指针 我看待它的方式是,如果我在函数定义中使用(*foo(int n)),则此函数foo(int n)的返回类型将成为函数指针。这是正确的吗?
有一个更简单的例子吗?

3 个答案:

答案 0 :(得分:3)

那么,让我们看看如何声明函数指针。

return-type (*function-name)(parameter-list);

在您发布的声明中,有两种函数指针类型在起作用。第一个是传递给与signal原型匹配的函数的参数:

void (*signal(int sig, void (*func)(int)))(int);
//                     ^^^^^^^^^^^^^^^^^

让我们将该函数指针类型重命名为handler并给它自己的声明。

typedef void (*handler)(int);
void (*signal(int sig, handler func))(int);

现在我们可以分解声明的其余部分。 “内部”部分是实际的函数声明:

...signal(int sig, handler func)...

“outside”描述了它返回的函数指针:

void (...)(int);

这也是与handler类型相同的函数指针类型,因此在typedef到位的情况下,我们可以像这样重新声明signal函数:

handler signal(int sig, handler func);

(更漂亮。)

答案 1 :(得分:1)

void (*signal(stuff))(int)

声明signal为返回指向函数的指针,该函数将int作为参数并返回void。这些东西给出了信号的参数,在这种情况下是

(int sig, void (*func)(int))

也就是说,函数信号的第一个参数是一个int,第二个参数是一个函数指针,它将int作为参数并返回void。

编辑:因此,如果您拨打电话 - 例如,

void foo (int x) {
    return;
}
void *bar = (*signal)(0, &foo);

然后bar将是一个指向函数的指针,该函数采用int并且不返回任何内容,因此可以按如下方式调用:

(*bar)(0);

答案 2 :(得分:1)

我们可以使用typedef来简化函数指针定义,这可以帮助您理解冗长而复杂的定义。

#include <stdio.h>
typedef void (*func)(int);
typedef void (*rtype)(int);

void myfunc(int a)
{
    printf("A is %d\n", a);
}

// thus signal can be defined as this
// exactly the same as in your question
rtype signal(int a, func handler)
{
    return myfunc;
}

int main()
{
    signal(0, 0)(12);
    return 0;
}

以上代码应输出:A is 12;

希望有所帮助!