For faster navigation, this Iframe is preloading the Wikiwand page for 回调函数.

回调函数

回调通常与原始调用者处于相同的抽象层

计算机编程中,回调函数或简称回调(callback),是指对某一段可执行代码引用,它被作为參數传递给另一段代码;预期这段代码将回调(执行)这个回调函数作为自己工作的一部份。这种执行可以是即时的,如在同步回调之中;也可以在后来的时间点上发生,如在异步回调之中。

编程语言以不同方式支持回调,经常将它们实现为子例程lambda表达式函数指针

使用

回调的用途十分广泛。例如,假设有一个函数,其功能为读取配置文件并由文件内容设置对应的选项。若这些选项由散列值所标记,则让这个函数接受一个回调会使得程序设计更加灵活:函数的调用者可以使用所希望的散列算法,该算法由一个将选项名转变为散列值的回调函数实现;因此,回调允许函数调用者在运行时调整原始函数的行为。

回调的另一种用途在于处理信号或者类似物。例如一个POSIX程序可能在收到SIGTERM信号时不愿立即终止;为了保证一切运行良好,该程序可以将清理函数注册为SIGTERM信号对应的回调。

回调亦可以用于控制一个函数是否作为:Xlib允许自定义的谓词用于决定程序是否希望处理特定的事件。

例子

下列C语言代码描述了利用回调处理POSIX风格的信号(在本示例中为SIGUSR1)的过程。值得注意的是,在处理信号的过程中,调用printf(3)不安全的

#include <stdio.h>
#include <signal.h>
#include <unistd.h>

void sig(int signum)
{
    printf("Received signal number %d!\n", signum);
}

int main(int argc, char *argv[])
{
    signal(SIGUSR1, sig);

    pause();
   
    return 0;
}

系统调用pause(3)会导致这个例子不做任何有意义的事,但这样做可以给你充分的时间来给这个进程发送信号。(在类Unix系统上,可以调用kill -USR1 <pid>,其中<pid>代表该程序的进程号。运行之后,该程序应当会有反应。)

实现

回调的形式因程序设计语言而有差别。

  • Objective-C中允许利用@selector关键字传递SEL类型的函数名。在实现中,SEL类型被定义为函数名字符串。
  • .NET语言中用到的事件与事件处理函数提供了用于回调的通用语法。
  • Apple或是LLVM的C语言扩展中,包含称为的语言特性,可以作为函数的参数传递,作为回调的一种实现。
  • 在缺少函数类型的参数的面向对象的程序语言中,例如Java,回调可以用传递抽象类或接口来模拟。回调的接收者会调用抽象类或接口的方法,这些方法由调用者提供实现。这样的对象通常是一些回调函数的集合,同时可能包含它所需要的数据。这种方法在实现某些设计模式时比较有用,例如访问者模式观察者模式策略模式
  • C++允许对象提供其自己的函数调用操作的实现,即重载operator()。标准模板库和函数指针一样接受这类对象(称为函数对象)作为各种算法的参数。

参见

参考资料

  1. ^ Perl Cookbook - 11.4. Taking References to Functions. [2008-03-03]. (原始内容存档于2008-04-10). 
  2. ^ Advanced Perl Programming - 4.2 Using Subroutine References. [2008-03-03]. (原始内容存档于2008-07-05). 

外部链接

{{bottomLinkPreText}} {{bottomLinkText}}
回调函数
Listen to this article

This browser is not supported by Wikiwand :(
Wikiwand requires a browser with modern capabilities in order to provide you with the best reading experience.
Please download and use one of the following browsers:

This article was just edited, click to reload
This article has been deleted on Wikipedia (Why?)

Back to homepage

Please click Add in the dialog above
Please click Allow in the top-left corner,
then click Install Now in the dialog
Please click Open in the download dialog,
then click Install
Please click the "Downloads" icon in the Safari toolbar, open the first download in the list,
then click Install
{{::$root.activation.text}}

Install Wikiwand

Install on Chrome Install on Firefox
Don't forget to rate us

Tell your friends about Wikiwand!

Gmail Facebook Twitter Link

Enjoying Wikiwand?

Tell your friends and spread the love:
Share on Gmail Share on Facebook Share on Twitter Share on Buffer

Our magic isn't perfect

You can help our automatic cover photo selection by reporting an unsuitable photo.

This photo is visually disturbing This photo is not a good choice

Thank you for helping!


Your input will affect cover photo selection, along with input from other users.

X

Get ready for Wikiwand 2.0 🎉! the new version arrives on September 1st! Don't want to wait?