PHP5添加了一项新的功能:Reflection。这个功能使得程序员可以reverse-engineer class, interface,function,method and extension。通过PHP代码,就可以得到某object的所有信息,并且可以和它交互。
假设有一个类Person:
05
|
private$_allowDynamicAttributes=
false;
|
20
|
publicfunctionsetId($v)
|
24
|
publicfunctiongetName()
|
28
|
publicfunctionsetName($v)
|
32
|
publicfunctiongetBiography()
|
34
|
return$this->biography;
|
36
|
publicfunctionsetBiography($v)
|
通过ReflectionClass,我们可以得到Person类的以下信息:
- 常量 Contants
- 属性 Property Names
- 方法 Method Names
- 静态属性 Static Properties
- 命名空间 Namespace
- Person类是否为final或者abstract
只要把类名"Person"传递给ReflectionClass就可以了:
1
|
$class=newReflectionClass('Person');
|
获取属性(Properties):
1
|
$properties=$class->getProperties();
|
2
|
foreach($propertiesas$property)
{
|
3
|
echo$property->getName()."\n";
|
默认情况下,ReflectionClass会获取到所有的属性,private 和 protected的也可以。如果只想获取到private属性,就要额外传个参数:
1
|
$private_properties=$class->getProperties(ReflectionProperty::IS_PRIVATE);
|
可用参数列表:
- ReflectionProperty::IS_STATIC
- ReflectionProperty::IS_PUBLIC
- ReflectionProperty::IS_PROTECTED
- ReflectionProperty::IS_PRIVATE
如果要同时获取public 和private 属性,就这样写:ReflectionProperty::IS_PUBLIC | ReflectionProperty::IS_PROTECTED
应该不会感觉陌生吧。
通过$property->getName()可以得到属性名,通过getDocComment可以得到写给property的注释。
01
|
foreach($propertiesas$property)
{
|
02
|
if($property->isProtected())
{
|
03
|
$docblock=$property->getDocComment();
|
04
|
preg_match('/
type\=([a-z_]*) /',$property->getDocComment(),$matches);
|
有点不可思议了吧。竟然连注释都可以取到。
获取方法(methods):通过getMethods() 来获取到类的所有methods。返回的是ReflectionMethod对象的数组。不再演示。
最后通过ReflectionMethod来调用类里面的method。
01
|
$data=array("id"=>
1,"name"=>"Chris","biography"=>"I
am am a PHP developer");
|
02
|
foreach($dataas$key=>$value)
{
|
03
|
if(!$class->hasProperty($key))
{
|
04
|
thrownewException($key."
is not a valid property");
|
07
|
if(!$class->hasMethod("get".ucfirst($key)))
{
|
08
|
thrownewException($key."
is missing a getter");
|
11
|
if(!$class->hasMethod("set".ucfirst($key)))
{
|
12
|
thrownewException($key."
is missing a setter");
|
19
|
$setter=$class->getMethod("set".ucfirst($key));
|
20
|
$ok=$setter->invoke($object,$value);
|
23
|
$setter=$class->getMethod("get".ucfirst($key));
|
24
|
$objValue=$setter->invoke($object);
|
27
|
if($value==$objValue)
{
|
28
|
echo"Getter
or Setter has modified the data.\n";
|
30
|
echo"Getter
and Setter does not modify the data.\n";
|
有点意思吧。