百分百源码网-让建站变得如此简单! 登录 注册 签到领金币!

主页 | 如何升级VIP | TAG标签

当前位置: 主页>网站教程>网页制作> PHP运用Closure新建匿名函数的办法介绍
分享文章到:

PHP运用Closure新建匿名函数的办法介绍

发布时间:09/01 来源:未知 浏览: 关键词:

Closure 类

用于代表匿名函数的类。

匿名函数(在 PHP 5.3 中被引入)会发生这个类型的对象。在过去,这个类被认为是一个实现细节,但此刻可以依靠它做一些事情。自 PHP 5.4 起,这个类带有一些办法,同意在匿名函数创立后对其停止更多的操纵。

这个类不克不及实例化,里面主要有两个办法,都用来复制闭包,一个静态一个动态,下面离别具体讲解下这两个不好懂得的办法。

Closure::bind

public static Closure Closure::bind ( Closure $closure , object $newthis [, mixed $newscope = 'static' ] )

参数说明:
closure
需要绑定的匿名函数。

newthis
需要绑定到匿名函数的对象,或者 NULL 创立未绑定的闭包。

newscope
想要绑定给闭包的类作用域,或者 'static' 表示不改动。假如传入一个对象,则使用这个对象的类型名。 类作用域用来决议在闭包中 $this 对象的 
私有、庇护办法 的可见性。 The class scope to which associate the closure is to be associated, or 'static' to keep the 
current one. If an object is given, the type of the object will be used instead. This determines the visibility of 
protected and private methods of the bound object.

参数说明:

  • closure需要绑定的匿名函数。

  • newthis需要绑定到匿名函数的对象,或者 NULL 创立未绑定的闭包。

  • newscope想要绑定给闭包的类作用域,或者 'static' 表示不改动。假如传入一个对象,则使用这个对象的类型名。 类作用域用来决议在闭包中 $this 对象的 私有、庇护办法 的可见性。

The class scope to which associate the closure is to be associated, or 'static' to keep the

current one. If an object is given, the type of the object will be used instead. This determines the visibility of

protected and private methods of the bound object.

上面是该办法的定义,

第一个参数很好懂得,就是一个闭包函数;

第二个参数就不太好懂得,假如要复制的闭包中包括$this,这个对象就表示这个$this,闭包函数里面临这个对象的修改在调取完毕之后也会保持一致,比方修改了一个属性;

第三个参数就不太好懂得了,看官方的说明也是云里雾里的,默许参数状况下,调取$this->拜访object $newthis中的属性函数的时候,会有限制,只能拜访public属性的函数,假如想拜访protected/private属性,就要设定为对应的类名/类实例,就要像在类里面一样,要拜访阿谁类的庇护/私有属性函数。

例子

<?php
class T {
    private function show()
    {
        echo "我是T里面的私有函数:show\n";
    }

    protected  function who()
    {
        echo "我是T里面的庇护函数:who\n";
    }

    public function name()
    {
        echo "我是T里面的公共函数:name\n";
    }
}

$test = new T();

$func = Closure::bind(function(){
    $this->who();
    $this->name();
    $this->show();
}, $test);

$func();

上面的代码会报错Fatal error: Uncaught Error: Call to protected method T::who() from context 'Closure'。 加上bind第三个参数为t::class或者new T(),会正常输出每一个结果。

我是T里面的庇护函数:who
我是T里面的公共函数:name
我是T里面的私有函数:show

当然了,闭包也可以传递参数

$test = new StdClass();
var_dump($test);

$func = Closure::bind(function($obj){
    $obj->name = "燕睿涛";
}, null);

$func($test);
var_dump($test);

上面的程序跟匿名函数一样,啥对象也没有依靠,上面的程序会输出:

object(stdClass)#1 (0) {
}
object(stdClass)#1 (1) {
  ["name"]=>
  string(9) "燕睿涛"
}

别的还有个特殊要说明的例子

<?php
class T {
    private function show()
    {
        echo "我是T里面的私有函数:show\n";
    }

    protected  function who()
    {
        echo "我是T里面的庇护函数:who\n";
    }

    public function name()
    {
        echo "我是T里面的公共函数:name\n";
    }
}

$func = Closure::bind(function ($obj) {
    $obj->show();
}, null);

$test = new T();

$func($test);

上面的状况会输出什么呢,没错,会报错,提醒拜访不了私有属性show,这个时候,加上第三个参数就可以了,看了第三个参数不但影响$this的作用域,
也可以影响参数的作用域。

Closure::bindTo

bindTobind功效相似,这里只是别的一种情势,都是复制当前闭包对象,绑定指定的$this对象和类作用域。,参数比bind少了第一个,
后面两个一样,当然还有一个不同就是bindTo不是静态办法,是闭包才会存在的一个属性办法。

例子

<?php
class T {
    private function show()
    {
        echo "我是T里面的私有函数:show\n";
    }

    protected  function who()
    {
        echo "我是T里面的庇护函数:who\n";
    }

    public function name()
    {
        echo "我是T里面的公共函数:name\n";
    }
}

$func = function () {
    $this->show();
    $this->who();
    $this->name();
};

$funcNew = $func->bindTo(new T(), T::class);

$funcNew();

上面函数的输出和bind的相似

我是T里面的私有函数:show
我是T里面的庇护函数:who
我是T里面的公共函数:name

一个trick

这个函数是在看composer生成的主动加载源码的时候碰到的,在composer中用的比力特殊,下面是截取部分composer中的代码

// 文件autoload_real.php
call_user_func(\Composer\Autoload\ComposerStaticInit898ad46cb49e20577400c63254121bac::getInitializer($loader));

// 文件autoload_static.php
public static function getInitializer(ClassLoader $loader)
{
    return \Closure::bind(function () use ($loader) {
        $loader->prefixLengthsPsr4 = ComposerStaticInit25885cdf386fdaafc0bce14bb5a7d06e::$prefixLengthsPsr4;
        $loader->prefixDirsPsr4 = ComposerStaticInit25885cdf386fdaafc0bce14bb5a7d06e::$prefixDirsPsr4;
        $loader->prefixesPsr0 = ComposerStaticInit25885cdf386fdaafc0bce14bb5a7d06e::$prefixesPsr0;
        $loader->classMap = ComposerStaticInit25885cdf386fdaafc0bce14bb5a7d06e::$classMap;

    }, null, ClassLoader::class);
}

上面的代码比力独特,在call_user_func中,第一感受是传错参数了,其实不然,这里调取了一个函数,这个函数会返回一个Closure对象,
也就是一个匿名函数,终究传入的参数还是一个callable类型。再看看这个返回的闭包,里面使用了use,这是连接闭包和外部变量的桥梁。
至于这里为什么一般传参数就可以,是由于php5里面,对象形参和实参数指向雷同的对象,函数里面临对象的修改会反映到对象外面。

所以,上面这么做是没问题的,还有别的一种情势也可以

call_user_func(\Composer\Autoload\ComposerStaticInit898ad46cb49e20577400c63254121bac::getInitializer(), $loader);

public static function getInitializer()
{
    return \Closure::bind(function ($loader) {
        $loader->prefixLengthsPsr4 = ComposerStaticInit25885cdf386fdaafc0bce14bb5a7d06e::$prefixLengthsPsr4;
        $loader->prefixDirsPsr4 = ComposerStaticInit25885cdf386fdaafc0bce14bb5a7d06e::$prefixDirsPsr4;
        $loader->prefixesPsr0 = ComposerStaticInit25885cdf386fdaafc0bce14bb5a7d06e::$prefixesPsr0;
        $loader->classMap = ComposerStaticInit25885cdf386fdaafc0bce14bb5a7d06e::$classMap;

    }, null, ClassLoader::class);
}

总结

好长时间没写blog了,有时候太焦躁,静不下心来,有时又有没有寻到想写的东西。还是得静下心来,好好做好每一件事,遇事情不要焦躁,心放大,相安无事的处置每一件事。

相关教程引荐:《PHP教程》

以上就是PHP使用Closure创立匿名函数的办法介绍的具体内容,更多请关注百分百源码网其它相关文章!

打赏

打赏

取消

感谢您的支持,我会继续努力的!

扫码支持
扫码打赏,你说多少就多少

打开支付宝扫一扫,即可进行扫码打赏哦

百分百源码网 建议打赏1~10元,土豪随意,感谢您的阅读!

共有151人阅读,期待你的评论!发表评论
昵称: 网址: 验证码: 点击我更换图片
最新评论

本文标签

广告赞助

能出一分力是一分吧!

订阅获得更多模板

本文标签

广告赞助

订阅获得更多模板