使い道はないような気がするけど、裏技っぽいやつ。
まずこういうクラスがあったとする。
<?php
class Person
{
protected $name;
protected $age;
function __construct($name, $age)
{
$this->name = $name;
$this->age = $age;
}
protected function greet()
{
echo "{$this->name}です。こんにちはこんにちは!\n";
}
}
Personのインスタンスが渡されたとき、Personと無関係の文脈ではnameやageは参照することができない。greetメソッドも実行することができない。(Reflectionでいじれば可能だけど、ここでは表題通り使わないことにする)
こんな継承クラスを一個作ると、抜き取ることができる。
<?php
class CrazyPerson extends Person
{
static function getProtected(Person $p, $memberName)
{
return $p->$memberName;
}
static function execProtected(Person $p, $methodName, array $args=[])
{
return call_user_func_array($p, $methodName, $args);
}
}
使い方。
<?php
function doSomething(Person $p) {
//$pのnameがどうしても取りたい!
echo CrazyPerson::getProtected($p, 'name');
//$pのgreet()をどうしても呼びたい!
CrazyPerson::execProtected($p, 'greet');
}
子クラスのコンテキストであれば、親クラスのprotectedが参照できる。
つまり子クラスのstaticメソッドを経由するだけで、親クラスのprotectedメンバやprotectedメソッドを呼び出すことが可能。抜き取りたいオブジェクトに何かする必要はない。