Skip to main content

闭包和匿名函数

一、匿名函数

匿名函数(Anonymous functions),允许 临时创建一个没有指定名称的函数。

匿名函数其实就是没有名称的函数,匿名函数可以赋值给变量,还能像其他任何PHP函数对象那样传递。不过匿名函数仍然是函数,因此可以调用,还可以传入参数,适合作为函数或方法的回调。

理论上讲闭包和匿名函数是不同的概念,不过PHP将其视作相同的概念(匿名函数在PHP中也叫作闭包函数),所以下面提到闭包时指的也是匿名函数;反之亦然。

二、匿名函数的结构

1.代码结构

$fun = function($param){
    //todo
};
echo $fun('111');

2.代码演示

$fun = function($name){
    printf("Hello %s\r\n",$name);
};
echo $fun('Tinywan');

输出:

Hello Tinywan

三、闭包

为啥先说匿名函数那?

因为匿名函数(Anonymous functions),也叫闭包函数(closures),PHP官网把这两个认为一个概念,我这里先把二者区分开。

我认为闭包就是对匿名函数,又重新做了一次封装,把匿名函数作为普通参数传入,并且调用它。

闭包可以捕获外部环境中的变量,由于在php中是早绑定,在闭包定义时,传入闭包的值就确定了。 // 如果外部变量发生了改变,那么闭包中的变量是不会变的,而且我们在闭包中也不能修改外部值。

四、闭包结构

1.代码结构(无use)

//本身调用本身
function printStr() {
    $func = function( $str ) {
        echo $str;
    };
    $func( 'some string' );
}

printStr();

 

2.代码结构(无use)

//在函数中把匿名函数返回,并且调用它
function getPrintStrFunc() {
    $func = function( $str ) {
        echo $str;
    };
    return $func;
}

$printStrFunc = getPrintStrFunc();
$printStrFunc( 'some string' );

 

2.代码结构(有use)

使用 use 关键字来附加闭包状态更加常见,因此我们先来看这种方式。

使用 use 关键字把变量附加闭包上时,附加的变量会记住附加时赋给它的值。

function Car ($name){
  return function($statu)use($name){
    return sprintf("Car %s is %s", $name, $statu); 
  };
}
// 将车名封装在闭包中
$car = Car("bmw");
// 调用车的动作
// 输出--> "bmw is running"
echo $car("running");

返回:

Car bmw is running

分析一下:为何没有传递$statu,但是却可以有输出那?

实际上闭包对象实现了__invoke()魔术方法,只要变量名后有(),PHP就会查找并调用__invoke方法。

__invoke方法,就是当尝试以调用函数的方式调用一个对象时,__invoke() 方法会被自动调用,此处就是把running当做了参数处理。

五、闭包函数

1.array_map

array array_map ( callable $callback , array $array1 [, array $... ] )

为数组的每个元素应用回调函数

使用:

<?php
function cube($n)
{
    return($n * $n * $n);
}

$a = array(1, 2, 3, 4, 5);
$b = array_map("cube", $a);
print_r($b);
?>

2.array_wake

bool array_walk ( array &$array , callable $callback [, mixed $userdata = NULL ] )

使用用户自定义函数对数组中的每个元素做回调处理

使用:

<?php
function myfunction($value,$key)
{
echo "The key $key has the value $value<br>";
}
$a=array("a"=>"red","b"=>"green","c"=>"blue");
array_walk($a,"myfunction");
?>

 

发表评论

电子邮件地址不会被公开。 必填项已用*标注

69 + = 79