Закрытие PHP и неявная область видимости глобальной переменной - PullRequest
9 голосов
/ 29 октября 2010

Есть ли способ, которым можно неявно объявить переменные верхнего уровня как глобальные для использования в замыканиях?

Например, если вы работаете с таким кодом:

$a = 0; //A TOP-LEVEL VARIABLE

Alpha::create('myAlpha')
    ->bind(DataSingleton::getInstance()
        ->query('c')
    )
    ->addBeta('myBeta', function($obj){
        $obj->bind(DataSingleton::getInstance()
                ->query('d')
            )
            ->addGamma('myGamma', function($obj){
                $obj->bind(DataSingleton::getInstance()
                        ->query('a')
                    )
                    ->addDelta('myDelta', function($obj){
                        $obj->bind(DataSingleton::getInstance()
                            ->query('b')
                        );
                    });
            })
            ->addGamma('myGamma', function($obj){

                $a++; //OUT OF MY SCOPE

                $obj->bind(DataSingleton::getInstance()
                        ->query('c')
                    )
                    .
                    .
                    .

Закрытия вызываются из метода как такового:

    public function __construct($name, $closure = null){
        $this->_name = $name;
        is_callable($closure) ? $closure($this) : null;
    }

Итак, в итоговом / TL; DR, есть способ неявно объявить переменные глобальными для использования в замыканиях (или, я полагаю, других функциях) без использования ключевого слова global или $GLOBALS глобальный

Я начал эту тему на другом часто посещаемом форуме (http://www.vbforums.com/showthread.php?p=3905718#post3905718)

1 Ответ

32 голосов
/ 29 октября 2010

Вы должны объявить их в определении закрытия:

->addBeta('myBeta', function($obj) use ($a) { // ...

В противном случае вы должны использовать ключевое слово global. Вы должны делать это для каждого замыкания, которое также использует $a.

...