ホームページ  >  記事  >  バックエンド開発  >  PHPのClosureクラスの詳しい説明

PHPのClosureクラスの詳しい説明

小云云
小云云オリジナル
2018-03-22 09:48:462572ブラウズ

この記事では主に、PHP の Closure クラスについて詳しく説明します。PHP Closure クラスは、匿名関数 (PHP 5.3 で導入) を表すために使用されるクラスであり、このタイプのオブジェクトを生成します。クラスは次のとおりです:

Closure {
    __construct ( void )
    public static Closure bind (Closure $closure , object $newthis [, mixed $newscope = 'static' ])
    public Closure bindTo (object $newthis [, mixed $newscope = 'static' ])
}

メソッドの説明:

Closure::__construct — インスタンス化を禁止するために使用されるコンストラクター
Closure::bind — クロージャーをコピーし、指定された $this オブジェクトとクラス スコープをバインドします。
Closure::bindTo — 現在のクロージャ オブジェクトをコピーし、指定された $this オブジェクトとクラス スコープをバインドします。

ここにリストされているメソッドに加えて、__invoke メソッドもあります。これは、 __invoke() マジック メソッドを実装する他のオブジェクトとの一貫性を保つためですが、クロージャー オブジェクトを呼び出すプロセスはそれとは何の関係もありません。

以下では、Closure::bindClosure::bindToを紹介します。

Closure::bind は Closure::bindTo の静的バージョンであり、その説明は次のとおりです:

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

closure はバインドする必要があるクロージャ オブジェクトを表します。
newthis は、クロージャ オブジェクトにバインドする必要があるオブジェクト、またはバインドされていないクロージャを作成する場合は NULL を示します。
newscope は、クロージャにバインドするクラス スコープを表します。クラス名またはクラスの例を渡すことができます。これは変更なしを意味します。

このメソッドは、成功すると新しい Closure オブジェクトを返し、失敗すると FALSE を返します。

説明例:

<?php
/** 
 * 复制一个闭包,绑定指定的$this对象和类作用域。 
 * 
 * @author 疯狂老司机 
 */
class Animal {
    private static $cat = "cat";
    private $dog = "dog";
    public $pig = "pig";
}

/* 
 * 获取Animal类静态私有成员属性
 */
$cat = static function() {
    return Animal::$cat;
};

/* 
 * 获取Animal实例私有成员属性
 */
$dog = function() {
    return $this->dog;
};

/* 
 * 获取Animal实例公有成员属性
 */
$pig = function() {
    return $this->pig;
};

$bindCat = Closure::bind($cat, null, new Animal());// 给闭包绑定了Animal实例的作用域,但未给闭包绑定$this对象
$bindDog = Closure::bind($dog, new Animal(), &#39;Animal&#39;);// 给闭包绑定了Animal类的作用域,同时将Animal实例对象作为$this对象绑定给闭包
$bindPig = Closure::bind($pig, new Animal());// 将Animal实例对象作为$this对象绑定给闭包,保留闭包原有作用域
echo $bindCat(),&#39;<br>&#39;;// 根据绑定规则,允许闭包通过作用域限定操作符获取Animal类静态私有成员属性
echo $bindDog(),&#39;<br>&#39;;// 根据绑定规则,允许闭包通过绑定的$this对象(Animal实例对象)获取Animal实例私有成员属性
echo $bindPig(),&#39;<br>&#39;;// 根据绑定规则,允许闭包通过绑定的$this对象获取Animal实例公有成员属性
?>

出力:

cat
dog
pig

Closure::bindTo — 現在のクロージャ オブジェクトをコピーし、指定された $this オブジェクトとクラス スコープをバインドします。説明は次のとおりです。

newthis はクロージャ オブジェクトにバインドされたオブジェクトを表し、バインドを解除するには NULL を表します。

newscope は、クロージャ オブジェクトに関連付けられたクラス スコープを表します。デフォルト値は 'static' で、変更なしを意味します。

このメソッドは、現在のオブジェクトと同じ変数をバインドするクロージャ オブジェクトを作成して返しますが、異なるオブジェクトや新しいクラス スコープをバインドすることもできます。バインドされたオブジェクトは、返されたクロージャ オブジェクトの $this の値を決定し、クラス スコープは、返されたクロージャ オブジェクトが呼び出すことができるメソッドを決定します。つまり、現時点で $this が呼び出すことができるメソッドは、newscope クラスで動作します。ドメインは同じです。

例 1:

public Closure Closure::bindTo (object $newthis [, mixed $newscope = &#39;static&#39; ])

Template.php テンプレート クラス


<?php
function __autoload($class) {
    require_once "$class.php";
}

$template = new Template;
$template->render(new Article, &#39;tpl.php&#39;);
?>

Article.php 情報クラス

<?php
/** 
 * 模板类,用于渲染输出 
 * 
 * @author 疯狂老司机 
 */
class Template{
    /**
     * 渲染方法
     *
     * @access public 
     * @param obj 信息类
     * @param string 模板文件名
     */
    public function render($context, $tpl){
        $closure = function($tpl){
            ob_start();
            include $tpl;
            return ob_end_flush();
        };
        $closure = $closure->bindTo($context, $context);
        $closure($tpl);
    }

}

tpl.php テンプレート ファイル

<?php
/** 
 * 文章信息类 
 * 
 * @author 疯狂老司机 
 */
class Article{
    private $title = "这是文章标题";
    private $content = "这是文章内容";
}

実行時に上記のファイルが同じレベルのディレクトリにあることを確認してください。

出力:

これは記事のタイトルです

これは記事の内容です

例 2:

<!DOCTYPE html PUBLIC "-//W3C//DTD XHTML 1.0 Transitional//EN" "http://www.w3.org/TR/xhtml1/DTD/xhtml1-transitional.dtd">
<html xmlns="http://www.w3.org/1999/xhtml" xml:lang="en">
    <head>
        <meta http-equiv="Content-Type" content="text/html;charset=UTF-8">
    </head>
    <body>
        <h1><?php echo $this->title;?></h1>
        <p><?php echo $this->content;?></p>
    </body>
</html>

出力:

dog

例 3:

<?php
/** 
 * 给类动态添加新方法
 * 
 * @author 疯狂老司机
 */
trait DynamicTrait {

    /**
     * 自动调用类中存在的方法
     */
    public function __call($name, $args) {
        if(is_callable($this->$name)){
            return call_user_func($this->$name, $args);
        }else{
            throw new \RuntimeException("Method {$name} does not exist");
        }
    }
    /**
     * 添加方法
     */
    public function __set($name, $value) {
        $this->$name = is_callable($value)? 
            $value->bindTo($this, $this): 
            $value;
    }
}

/** 
 * 只带属性不带方法动物类
 * 
 * @author 疯狂老司机
 */
class Animal {
    use DynamicTrait;
    private $dog = &#39;dog&#39;;
}

$animal = new Animal;

// 往动物类实例中添加一个方法获取实例的私有属性$dog
$animal->getdog = function() {
    return $this->dog;
};

echo $animal->getdog();

?>

出力:

132.88


追加説明: クロージャUSE キーを使用して外部変数を接続できます。

要約: クロージャを適切に使用すると、コードをより簡潔で洗練されたものにすることができます。

関連する推奨事項:

phpでのクロージャの使用例の紹介

phpでのクロージャの使用例の詳細な説明

phpでのクロージャの紹介

以上がPHPのClosureクラスの詳しい説明の詳細内容です。詳細については、PHP 中国語 Web サイトの他の関連記事を参照してください。

声明:
この記事の内容はネチズンが自主的に寄稿したものであり、著作権は原著者に帰属します。このサイトは、それに相当する法的責任を負いません。盗作または侵害の疑いのあるコンテンツを見つけた場合は、admin@php.cn までご連絡ください。