本文已参与「新人创作礼」活动,一起开启掘金创作之路。
前言
努力学习中,目前对回调函数的思想还是不能很好地理解,如有错误欢迎前往评论区留言
一、callback回调函数定义
回调函数(callback)是什么? - 知乎 (zhihu.com)
直接运行一个函数被称为直调
# 直调
<?php
function hello(){
echo "hello";
}
hello();
而通过一个函数(中间函数)调用另一个函数(回调函数)被称为回调,中间函数已经定义好回调函数执行完成后的其他动作了,我们在主程序直接调用此中间函数即可
回调函数不是由该函数的实现方直接调用,而是在特定的事件或条件发生时由另外的一方调用的,用于对该事件或条件进行响应。
# 回调
# run()是中间函数
# hello()是回调函数
# 回调是通过call_user_func()实现的
<?php
function run($func, $param){
call_user_func($func, $param);
echo "Run done!<br/>";
}
function hello($param){
echo "hello".$param."<br/>";
}
run("hello", 1);
“你到一个商店买东西,刚好你要的东西没有货,于是你在店员那里留下了你的电话,过了几天店里有货了,店员就打了你的电话,然后你接到电话后就到店里去取了货。在这个例子里,你的电话号码就叫回调函数,你把电话留给店员就叫登记回调函数,店里后来有货了叫做触发了回调关联的事件,店员给你打电话叫做调用回调函数,你到店里去取货叫做响应回调事件。回答完毕。“
(摘自知乎 作者:常溪玲)
二、call_user_func()和call_user_func_array()
PHP使用call_user_func()和call_user_func_array()回调
# 函数原型
call_user_func ( callable $callback , mixed $parameter = ? , mixed $... = ? ) : mixed
call_user_func_array ( callable $callback , array $param_arr ) : mixed
二者区别在于前者传参上散装的,后者传参上需要封成array
三、回调的实现
Ⅰ、回调普通函数
<?php
function test($a, $b){
echo $a.$b."<br/>"
}
call_user_func('test', 1, 2);
call_user_func_array('test', array(1, 2));
Ⅱ、回调类函数
第一个传参为array,包含对象名和函数名,需实例化
<?php
class Test{
function t1($a){
echo 't1 '.$a.'<br/>';
}
public static t2($a){
echo 'static t2'.$a.'<br/>';
}
}
$test = new Test();
call_user_func(array($test, 't1'), 1);
Ⅲ、回调类静态函数
第一个传参为array,包含类名和函数名,无需实例化
<?php
class Test{
function t1($a){
echo 't1 '.$a.'<br/>';
}
public static t2($a){
echo 'static t2'.$a.'<br/>';
}
}
call_user_func(array('Test', 't2'), 1);
四、为什么不采用$func()?
回到最开始的示例代码
<?php
function run($func, $param){
call_user_func($func, $param);
echo "Run done!<br/>";
}
function hello($param){
echo "hello".$param."<br/>";
}
run("hello", 1);
最开始很是不能理解为什么不修改成以下的写法:
<?php
function run($param){
hello($param); # changed
echo "Run done!<br/>";
}
function hello($param){
echo "hello".$param."<br/>";
}
run(1);
回调和直调其实并无区别,回调只是借助了一个中间函数间接调用另一个函数
使用回调的目的是:run函数可能是一个系统级函数、或者是其他我们无权修改的函数,而hello这个函数我们是可以自定义的,因此在中间函数调用的时候不能写的太具体,通过传参来达到一个类似接口的操作,这种采用回调的方法提高了中间函数-回调函数的灵活性:
<?php
function run($func, $param){
call_user_func($func, $param);
echo "Run done!<br/>";
}
function hello($param){
echo "hello".$param."<br/>";
}
function nihao($param){
echo "nihao".$param."<br/>";
}
function bonjour($param){
echo "bonjour".$param."<br/>";
}
run("hello", 1);
run("nihao", 2);
run("bonjour", 3);
如果打算新添加函数,那么在中间函数使用回调就很方便灵活了,直接对中间函数传入新添加的回调函数名称即可运行,这就体现了回调函数提高灵活性的作用了