Довольно сложно придумать название для этого вопроса, но в основном вот код:
<?php
class Sub {
protected $closure;
public function setClosure($closure) {
$this->closure = $closure;
}
public function callClosure() {
$this->closure->__invoke();
}
protected function outcome() {
echo 'calling from sub';
}
}
class Main {
public function __construct() {
$this->sub = new Sub();
}
public function start() {
$this->sub->setClosure(function() {
$this->outcome();
});
$this->sub->callClosure();
}
protected function outcome() {
echo 'calling from main';
}
}
$main = new Main();
$main->start();
Результатом этого является calling from main
, Однако это именно то, чего я хочу, так как я буду иметь дело с этим поведением, и я не до конца понимаю, почему это работает так, я хотел бы получить некоторые пояснения.
Перед написанием кода я ожидал, что он вызовет outcome
метод из Sub
класс, а не из Main
учебный класс. Использует ли закрытие $this
из области, из которой это было определено? Что делать, если по какой-то причине я хочу использовать $this
из области его вызова?
Работает правильно и согласно PHP анонимные функции ручной, потому что
Родительская область действия замыкания — это функция, в которой замыкание было
объявлен (не обязательно функция, из которой он был вызван)
В php эта анонимная функция реализована как Закрытие класса.
И как уже Марк Бейкер сказал, когда вы создаете свое закрытие внутри вашего Main
класс, вы автоматически получаете этот связанный объект и эту область видимости.
«Связанный объект» определяет значение $, которое будет иметь
Тело функции и «область видимости» представляет класс, который
определяет, какие частные и защищенные члены анонимной функции
будет иметь доступ. А именно, члены, которые будут видны
так же, как если бы анонимная функция была методом данного класса
в качестве значения параметра newscope.
В вашем случае этот класс Main
не Sub
Других решений пока нет …