如何在C中阅读这个复杂的声明?

如何在C中阅读这个复杂的声明?,c,C,可能重复: 我有一个复杂的声明,它取自“signal.h”头文件,下面是声明 void (*signal(int sig, void (*func)(int)))(int); 现在,我如何解析它?作为 signal是一个函数,它有两个参数'sig'为int类型,而'func'是指向以int为参数的函数的指针,返回void类型;它返回一个指向以int为参数并返回void的函数的指针 是正常还是信号是指向函数的指针?signal是一个函数,它接受两个参数并返回指向函数的指针,该函数将int作

可能重复:

我有一个复杂的声明,它取自“signal.h”头文件,下面是声明

  void (*signal(int sig, void (*func)(int)))(int);
现在,我如何解析它?作为

signal是一个函数,它有两个参数'sig'为int类型,而'func'是指向以int为参数的函数的指针,返回void类型;它返回一个指向以int为参数并返回void的函数的指针


是正常还是信号是指向函数的指针?

signal
是一个函数,它接受两个参数并返回指向函数的指针,该函数将
int
作为参数并返回
void

signal
采用的两个参数是
int
和指向函数的指针,该函数将
int
作为参数并返回
void

是的,你得到了正确的描述和总体想法。

使用

将信号声明为函数(int,指向函数的指针(int)返回void)返回指向函数的指针(int)返回void

输入

void (*signal(int, void(*)(int)))(int)
这意味着
信号
是一个函数。调用
信号的结果是指向函数
void f(int)
的指针


说明:
signal()
调用将安装一个新的信号处理程序并返回旧的信号处理程序(因此,如果需要,您可以稍后还原它)。

不,没错。signal接受两个参数,一个int和一个指向函数的指针,并返回指向函数的指针(签名与
func
参数相同)

它类似于(imo)更具可读性:

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

//参考约翰的答案进行编辑

从最左边的标识符开始,找出解决方法,记住
[]
()
*
之前绑定,所以
*a[]
是指针数组,
(*a)[]
是指向数组的指针,
*f()
是返回指针的函数,
(*f)(
是指向函数的指针:

       signal                                     -- signal
       signal(                          )         -- is a function
       signal(    sig,                  )         -- with a parameter named sig
       signal(int sig,                  )         --   of type int
       signal(int sig,        func      )         -- and a parameter named func
       signal(int sig,      (*func)     )         --   which is a pointer
       signal(int sig,      (*func)(   ))         --   to a function
       signal(int sig,      (*func)(int))         --     taking an int parameter
       signal(int sig, void (*func)(int))         --     and returning void
      *signal(int sig, void (*func)(int))         -- returning a pointer
     (*signal(int sig, void (*func)(int)))(   )   -- to a function
     (*signal(int sig, void (*func)(int)))(int)   --   taking an int parameter
void (*signal(int sig, void (*func)(int)))(int);  --   and returning void
void new_interrupt_handler(int sig)
{
  ... // do something interesting with interrupt signal
}

int main(void)
{
  void (*old_interrupt_handler)(int);
  ...
  /**
   * Set up our new interrupt handler
   */
  old_interrupt_handler = signal(SIGINT, new_interrupt_handler);
  ...
  /**
   * Restore original interrupt handler
   */
  signal(SIGINT, old_interrupt_handler);
  ...
}
signal
将信号处理程序函数
func
与信号
sig
关联,并返回指向旧信号处理程序函数的指针:

       signal                                     -- signal
       signal(                          )         -- is a function
       signal(    sig,                  )         -- with a parameter named sig
       signal(int sig,                  )         --   of type int
       signal(int sig,        func      )         -- and a parameter named func
       signal(int sig,      (*func)     )         --   which is a pointer
       signal(int sig,      (*func)(   ))         --   to a function
       signal(int sig,      (*func)(int))         --     taking an int parameter
       signal(int sig, void (*func)(int))         --     and returning void
      *signal(int sig, void (*func)(int))         -- returning a pointer
     (*signal(int sig, void (*func)(int)))(   )   -- to a function
     (*signal(int sig, void (*func)(int)))(int)   --   taking an int parameter
void (*signal(int sig, void (*func)(int)))(int);  --   and returning void
void new_interrupt_handler(int sig)
{
  ... // do something interesting with interrupt signal
}

int main(void)
{
  void (*old_interrupt_handler)(int);
  ...
  /**
   * Set up our new interrupt handler
   */
  old_interrupt_handler = signal(SIGINT, new_interrupt_handler);
  ...
  /**
   * Restore original interrupt handler
   */
  signal(SIGINT, old_interrupt_handler);
  ...
}


但这正是我被
typedefintfoo(void)
弄糊涂的地方:foo是指向函数的指针,但你可以将它设置为快捷方式并说它是函数,因为你可以执行
foox;x()@Benoit你能把它作为你的答案吗?我不确定我的问题是基于什么原因结束的,我问的问题与以前的问题不同。但在我的上下文中它不同,不是吗?@Aaron-你没有输入与OP相同的声明。@JohnBode:你是对的。修正了。+1用于链接到现在信号是如何指向函数的指针?它告诉信号是函数返回指针。现在真的很困惑,大多数答案说它的函数返回指针,而你说的是不同的。就像我在回答中说的,
()
*
之前绑定,所以
*f()
是一个返回指针的函数,不是指向函数的指针。
signal
的声明形式包括
*signal(…)
,因此
signal
肯定是一个返回指针的函数。谢谢@JohnBode的解释。我编辑了我的答案是错误的。+1非常好,一步一步解释。谢谢@John的想法,但这里的一些用户反对它,说信号是指向函数的指针。@Amit-在Aaron的例子中,他输入给cdecl的字符串不是您在问题中所写的字符串。+1您使用typedef作为函数指针的原因之一:这对大脑更容易。:)@netcoder:它当然可以使这样的声明更容易阅读,但我喜欢知道函数签名是什么样子,而不必搜索typedef<代码>sighandler func
没有告诉我如何使用
func
,而
void(*func)(int)
does.GNU调用它
signandler\t
,libc4和libc5调用它
SignalHandler
,glibc调用它
sig\u t
,顺便说一句;)这就是您应该如何编写代码。如果您在声明诸如“指向以函数指针为参数的函数的函数指针”这样晦涩难懂的东西时没有使用typedef,那么您就是邪恶的,而且可能相当愚蠢。