php面向对象视频笔记之第六章(反射机制与动态代理)

1、反射机制与动态代理
php的Reflection反射机制
 php5添加了一项新的功能:Reflection。这个功能使得程序员可以reflection class,interfacce,function,

method...。通过php代码,就可以得到某类/方法等的所有信息,并且可以和它交互。

php面向对象视频笔记之第六章(反射机制与动态代理)_第1张图片

 反射机制的应用:
   动态代理:也叫委托模式,在委托模式中,有两个对象参与处理同个请求,接受请求的对象将请求委托给另一
个对象来处理。
   插件系统:利用反射机制自动获取插件列表以及其它的相关信息。

ReflectionFunction应用示例如下即运行结果:

';
}

test();

$ref_fun = new ReflectionFunction('test');//参数即函数名

echo $ref_fun->getDocComment();//函数注释
echo '
定义在文件:',$ref_fun->getFileName();//函数定义所在的文件 echo '
代码开始行:',$ref_fun->getStartLine();//开始行 echo '
代码结束行:',$ref_fun->getEndLine();//结束行 try{ new ReflectionFunction('test1'); }catch(ReflectionException $e){ echo '
',$e->getMessage(); }
php面向对象视频笔记之第六章(反射机制与动态代理)_第2张图片

php用反射机制实现动态代理

ref.php

';
   }
   function t2($str){
      echo '我是一个带一个参数的方法t2,参数是:',$str,'
'; } private function t3(){ } static function t4(){ echo '我是一个静态方法
'; } } $a = new A(); $ref_cls = new ReflectionClass('A');//参数可是类名,也可是类的实例如new ReflectionClass($a); //获取类中的所有方法 $class_all_methods = $ref_cls->getMethods(); print_r($class_all_methods); echo '
以下是判断类中是否有某个方法的结果.
'; //判断类中是否有某个方法 hasMethod 返回布尔值 var_dump($ref_cls->hasMethod('t1'));//bool true echo '
'; var_dump($ref_cls->hasMethod('t')); //bool false echo '
'; echo '以下是判断类中某个方法权限和调用运行的结果.
'; //判断方法的修饰符 public protected private static //判断方式:is+修饰符 返回的是布尔值 //判断之前要获取类中的方法 $ref_method = $ref_cls->getMethod('t1');//参数是方法名 var_dump($ref_method->isPublic());//是否为公开方法 bool true echo '
'; //执行方法 //静态方法调用 invoke(null,参数); //普通方法调用 invoke(实例对象,参数); //私有方法不能被invoke调用。 if($ref_method->isPublic() && !$ref_method->isAbstract()){//是公开且非抽象。 if($ref_method->isStatic()){ $ref_method->invoke(null); }else{ $ref_method->invoke($a); } } //获取类中的方法的反射类(跟上面的方法作用一样) $ref_method = new ReflectionMethod('A','t3');//类名+方法名. var_dump($ref_method->isPublic());//是否为公开方法 bool false echo '
'; $ref_method = new ReflectionMethod('A','t2'); var_dump($ref_method->isStatic());//是否为静态方法 bool true echo '
'; if($ref_method->isPublic() && !$ref_method->isAbstract()){//是公开且非抽象。 if($ref_method->isStatic()){ $ref_method->invoke(null,'yi'); }else{ $ref_method->invoke($a,'yi'); } }

运行结果:

php面向对象视频笔记之第六章(反射机制与动态代理)_第3张图片

dynamic.php

';
  }
}
class C{
  function showInfoC(){
     echo 'function "showInfoC()" of Class C.
'; } } class B{ private $obj; function __construct(){ //$this->obj = new A();//添加单个数组元素 } function addObj($obj){ //动态添加对象数组 $this->obj[] = $obj; //依次后补数组元素 print_r($this->obj);//查看数组元素 echo '
'; } function __call($name,$args){ foreach($this->obj as $v){//遍历数组元素 $ref_cls = new ReflectionClass($v);//反射出该对象所在类名 if($ref_cls->hasMethod($name)){//判断该类是否有该方法 $ref_method = $ref_cls->getMethod($name); if($ref_method->isPublic() && !$ref_method->isAbstract()) { if($ref_method->isStatic()){ $ref_method->invoke(null); }else{ $ref_method->invoke($v); } } } } /*添加单个对象的情况 $ref_cls = new ReflectionClass($this->obj); if($ref_cls->hasMethod($name)){ $ref_method = $ref_cls->getMethod($name); if($ref_method->isPublic() && !$ref_method->isAbstract()) { if($ref_method->isStatic()){ $ref_method->invoke(null); }else{ $ref_method->invoke($this->obj); } } }*/ } } $b = new B(); $b->addObj(new A()); $b->addObj(new C()); $b->showInfoA(); $b->showInfoC();
运行结果:

php面向对象视频笔记之第六章(反射机制与动态代理)_第4张图片
插件雏形示例:

plugin.php:

 'My_menu1',
		   'link' => 'index.php?act=my_link1'
	     ),
		 array(
		   'name' => 'My_menu2',
		   'link' => 'index.php?act=my_link2' 	 
		 )	 
	  );

		 //print_r($menu);
		 return $menu;
   }
}

class YourPlugin implements Plugin{
   //获取插件菜单
   function showMenu(){
      $menu = array(
	     array(
		   'name' => 'Your_menu1',
		   'link' => 'index.php?act=your_link1'
	     ),
	     array(
		   'name' => 'Your_menu2',
		   'link' => 'index.php?act=your_link2' 
		 )		 
	  );

		 //print_r($menu);
		 return $menu;
   }
}


demo.php:

implementsInterface('Plugin')){
	    //echo $cls,'
'; if($ref_cls->hasMethod('showMenu')){ $ref_method = $ref_cls->getMethod('showMenu'); if($ref_method->isPublic() && !$ref_method->isAbstract()){ if($ref_method->isStatic()){ $menu = $ref_method->invoke(null); }else{ //通过反射类获取类的一个实例 //$menu = $ref_method->invoke(new $cls()); $instance = $ref_cls->newInstance(); $menu = $ref_method->invoke($instance); } //合并菜单 $menus = array_merge($menus,$menu); } } } } //print_r($menus); return $menus; } $menu_list = get_plugin_menus(); foreach($menu_list as $menu){ echo ''.$menu['name'].'
';//菜单超链接 }
运行结果:

php面向对象视频笔记之第六章(反射机制与动态代理)_第5张图片



你可能感兴趣的:(PHP)