问题
In the ReflectionMethod documentation, I can't find anything to know wether a method was inherited from its parent class or defined in the reflected class.
Edit: I use ReflectionClass::getMethods(). I want to know for each method if it has been defined in the class being reflected, or if it has been defined in a parent class. In the end, I want to keep only the methods defined in the current class.
class Foo {
function a() {}
function b() {}
}
class Bar extends Foo {
function a() {}
function c() {}
}
I want to keep a
and c
.
回答1:
You should be able to call ReflectionMethod::getDeclaringClass() to get the class declaring the method. Then a call to ReflectionClass::getParentClass() to get the parent class. Lastly a call to ReflectionClass::hasMethod() will tell you if the method was declared in the parent class.
Example:
<?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";
}
回答2:
You can get the ReflectionMethod
object for the method you are interested in, and then use getPrototype()
to get the ReflectionMethod
of the method in the parent class. If the method does not override a method in the parent, this will throw a ReflectionClass
exception.
The following example code will create an array with method name as key and the class which defined the implementation in use for the reflected class.
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);
This will print:
Array
(
[overridein3] => Base
[in2overridein3] => Base2
[in3only] => Base3
[overridein2] => Base
[in2only] => Base2
[basemethod] => Base
)
来源:https://stackoverflow.com/questions/9471883/php-reflection-how-to-know-if-a-reflectionmethod-is-inherited