PHP Reflection: Как узнать, наследуется ли ReflectionMethod? - PullRequest
4 голосов
/ 28 февраля 2012

В документации ReflectionMethod я не могу найти ничего, чтобы узнать, был ли метод унаследован от его родительского класса или определен в отраженном классе.

Редактировать: я использую ReflectionClass :: getMethods () . Я хочу знать для каждого метода, был ли он определен в отражаемом классе или определен в родительском классе. В конце я хочу оставить только методы, определенные в текущем классе.

class Foo {
    function a() {}
    function b() {}
}

class Bar extends Foo {
    function a() {}
    function c() {}
}

Я хочу оставить a и c.

Ответы [ 2 ]

5 голосов
/ 28 февраля 2012

Вы можете получить объект ReflectionMethod для интересующего вас метода, а затем использовать getPrototype(), чтобы получить ReflectionMethod метода в родительском классе.Если метод не переопределяет метод в родительском объекте, это вызовет исключение ReflectionClass.

В следующем примере кода будет создан массив с именем метода в качестве ключа и классом, который определил реализацию, используемую дляотраженный класс.

class Base {
    function basemethod() {}
    function overridein2() {}
    function overridein3() {}
}
class Base2 extends Base {
    function overridein2() {}
    function in2only() {}
    function in2overridein3 () {}
}
class Base3 extends Base2 {
    function overridein3() {}
    function in2overridein3 () {}
    function in3only() {}
}

$rc = new ReflectionClass('Base3');
$methods = array();
foreach ($rc->getMethods() as $m) {
    try {
        if ($m->getPrototype()) {
            $methods[$m->name] = $m->getPrototype()->class;
        }
    } catch (ReflectionException $e) {
        $methods[$m->name] = $m->class;
    }
}

print_r($methods);

Это напечатает:

Array
(
    [overridein3] => Base
    [in2overridein3] => Base2
    [in3only] => Base3
    [overridein2] => Base
    [in2only] => Base2
    [basemethod] => Base
)
5 голосов
/ 28 февраля 2012

Вы должны иметь возможность вызвать ReflectionMethod :: getDeclaringClass () , чтобы получить класс, объявляющий метод.Затем вызывается ReflectionClass :: getParentClass () , чтобы получить родительский класс.Наконец, вызов ReflectionClass :: hasMethod () скажет вам, был ли метод объявлен в родительском классе.

Пример:

<?php
class Foo {
    function abc() {}
}

class Bar extends Foo {
    function abc() {}
    function def() {}
}


$bar = new Bar();

$meth = new ReflectionMethod($bar, "abc");
$cls = $meth->getDeclaringClass();
$prnt = $cls->getParentClass();

if ($cls->hasMethod($meth->name)) {
    echo "Method {$meth->name} in Bar\n";
}
if ($prnt->hasMethod($meth->name)) {
    echo "Method {$meth->name} in Foo\n";
}

$meth = new ReflectionMethod($bar, "def");
$cls = $meth->getDeclaringClass();
$prnt = $cls->getParentClass();

if ($cls->hasMethod($meth->name)) {
    echo "Method {$meth->name} in Bar\n";
}
if ($prnt->hasMethod($meth->name)) {
    echo "Method {$meth->name} in Foo\n";
}
...