`
kaozjlin
  • 浏览: 117461 次
  • 性别: Icon_minigender_1
  • 来自: 福建
社区版块
存档分类
最新评论

PHP 反射机制详解 以及插件架构实现

    博客分类:
  • php
 
阅读更多
1。用途:
该扩展分析php程序,导出或提取出关于类、方法、属性、参数等的详细信息,包括注释。
Reflection可以说是对php库函数:“Classes/Objects 类/对象函数”的一个扩展。
主要用在通过程序检测现有php程序内部关于类、方法等信息,并做出处理。

2。API概览:
class Reflection { }
interface Reflector { }
class ReflectionException extends Exception { }
class ReflectionFunction implements Reflector { }
class ReflectionParameter implements Reflector { }
class ReflectionMethod extends ReflectionFunction { }
class ReflectionClass implements Reflector { }
class ReflectionObject extends ReflectionClass { }
class ReflectionProperty implements Reflector { }
class ReflectionExtension implements Reflector { }

3。详细说明:(例子详见php手册)
①Reflection类
<?php
class Reflection
{
    public static mixed export(Reflector r [,bool return])
    //导出一个类或方法的详细信息
    public static array getModifierNames(int modifiers)
    //取得修饰符的名字
}
?>

②ReflectionException类

该类继承标准类,没特殊方法和属性。

③ReflectionFunction类
<?php
class ReflectionFunction implements Reflector
{
    final private __clone()
    public object __construct(string name)
    public string __toString()
    public static string export()
    //导出该函数的详细信息
    public string getName()
    //取得函数名
    public bool isInternal()
    //测试是否为系统内部函数
    public bool isUserDefined()
    //测试是否为用户自定义函数
    public string getFileName()
    //取得文件名,包括路径名
    public int getStartLine()
    //取得定义函数的起始行
    public int getEndLine()
    //取得定义函数的结束行
    public string getDocComment()
    //取得函数的注释
    public array getStaticVariables()
    //取得静态变量
    public mixed invoke(mixed* args)
    //调用该函数,通过参数列表传参数
    public mixed invokeArgs(array args)
    //调用该函数,通过数组传参数
    public bool returnsReference()
    //测试该函数是否返回引用
    public ReflectionParameter[] getParameters()
    //取得该方法所需的参数,返回值为对象数组
    public int getNumberOfParameters()
    //取得该方法所需的参数个数
    public int getNumberOfRequiredParameters()
    //取得该方法所需的参数个数
}
?>

④ReflectionParameter类:
<?php
class ReflectionParameter implements Reflector
{
    final private __clone()
    public object __construct(string name)
    public string __toString()
    public static string export()
    //导出该参数的详细信息
    public string getName()
    //取得参数名
    public bool isPassedByReference()
    //测试该参数是否通过引用传递参数
    public ReflectionClass getClass()
    //若该参数为对象,返回该对象的类名
    public bool isArray()
    //测试该参数是否为数组类型
    public bool allowsNull()
    //测试该参数是否允许为空
    public bool isOptional()
    //测试该参数是否为可选的,当有默认参数时可选
    public bool isDefaultValueAvailable()
    //测试该参数是否为默认参数
    public mixed getDefaultValue()
    //取得该参数的默认值
}
?>

⑤ReflectionClass类:
<?php
class ReflectionClass implements Reflector
{
    final private __clone()
    public object __construct(string name)
    public string __toString()
    public static string export()
    //导出该类的详细信息
    public string getName()
    //取得类名或接口名
    public bool isInternal()
    //测试该类是否为系统内部类
    public bool isUserDefined()
    //测试该类是否为用户自定义类
    public bool isInstantiable()
    //测试该类是否被实例化过
    public bool hasConstant(string name)
    //测试该类是否有特定的常量
    public bool hasMethod(string name)
    //测试该类是否有特定的方法
    public bool hasProperty(string name)
    //测试该类是否有特定的属性
    public string getFileName()
    //取得定义该类的文件名,包括路径名
    public int getStartLine()
    //取得定义该类的开始行
    public int getEndLine()
    //取得定义该类的结束行
    public string getDocComment()
    //取得该类的注释
    public ReflectionMethod getConstructor()
    //取得该类的构造函数信息
    public ReflectionMethod getMethod(string name)
    //取得该类的某个特定的方法信息
    public ReflectionMethod[] getMethods()
    //取得该类的所有的方法信息
    public ReflectionProperty getProperty(string name)
    //取得某个特定的属性信息
    public ReflectionProperty[] getProperties()
    //取得该类的所有属性信息
    public array getConstants()
    //取得该类所有常量信息
    public mixed getConstant(string name)
    //取得该类特定常量信息
    public ReflectionClass[] getInterfaces()
    //取得接口类信息
    public bool isInterface()
    //测试该类是否为接口
    public bool isAbstract()
    //测试该类是否为抽象类
    public bool isFinal()
    //测试该类是否声明为final
    public int getModifiers()
    //取得该类的修饰符,返回值类型可能是个资源类型
    //通过Reflection::getModifierNames($class->getModifiers())进一步读取
    public bool isInstance(stdclass object)
    //测试传入的对象是否为该类的一个实例
    public stdclass newInstance(mixed* args)
    //创建该类实例
    public ReflectionClass getParentClass()
    //取得父类
    public bool isSubclassOf(ReflectionClass class)
    //测试传入的类是否为该类的父类
    public array getStaticProperties()
    //取得该类的所有静态属性
    public mixed getStaticPropertyValue(string name [, mixed default])
    //取得该类的静态属性值,若private,则不可访问
    public void setStaticPropertyValue(string name, mixed value)
    //设置该类的静态属性值,若private,则不可访问,有悖封装原则
    public array getDefaultProperties()
    //取得该类的属性信息,不含静态属性
    public bool isIterateable()
    public bool implementsInterface(string name)
    //测试是否实现了某个特定接口
    public ReflectionExtension getExtension()
    public string getExtensionName()
}
?>

⑥ReflectionMethod类:
<?php
class ReflectionMethod extends ReflectionFunction
{
    public __construct(mixed class, string name)
    public string __toString()
    public static string export()
    //导出该方法的信息
    public mixed invoke(stdclass object, mixed* args)
    //调用该方法
    public mixed invokeArgs(stdclass object, array args)
    //调用该方法,传多参数
    public bool isFinal()
    //测试该方法是否为final
    public bool isAbstract()
    //测试该方法是否为abstract
    public bool isPublic()
    //测试该方法是否为public
    public bool isPrivate()
    //测试该方法是否为private
    public bool isProtected()
    //测试该方法是否为protected
    public bool isStatic()
    //测试该方法是否为static
    public bool isConstructor()
    //测试该方法是否为构造函数
    public bool isDestructor()
    //测试该方法是否为析构函数
    public int getModifiers()
    //取得该方法的修饰符
    public ReflectionClass getDeclaringClass()
    //取得该方法所属的类
    // Inherited from ReflectionFunction
    final private __clone()
    public string getName()
    public bool isInternal()
    public bool isUserDefined()
    public string getFileName()
    public int getStartLine()
    public int getEndLine()
    public string getDocComment()
    public array getStaticVariables()
    public bool returnsReference()
    public ReflectionParameter[] getParameters()
    public int getNumberOfParameters()
    public int getNumberOfRequiredParameters()
}
?>

⑦ReflectionProperty类:
<?php
class ReflectionProperty implements Reflector
{
    final private __clone()
    public __construct(mixed class, string name)
    public string __toString()
    public static string export()
    //导出该属性的详细信息
    public string getName()
    //取得该属性名
    public bool isPublic()
    //测试该属性名是否为public
    public bool isPrivate()
    //测试该属性名是否为private
    public bool isProtected()
    //测试该属性名是否为protected
    public bool isStatic()
    //测试该属性名是否为static
    public bool isDefault()
    public int getModifiers()
    //取得修饰符
    public mixed getValue(stdclass object)
    //取得该属性值
    public void setValue(stdclass object, mixed value)
    //设置该属性值
    public ReflectionClass getDeclaringClass()
    //取得定义该属性的类
    public string getDocComment()
    //取得该属性的注释
}
?>

⑧ReflectionExtension类
<?php
class ReflectionExtension implements Reflector {
    final private __clone()
    public __construct(string name)
    public string __toString()

    public static string export()
    //导出该扩展的所有信息
    public string getName()
    //取得该扩展的名字
    public string getVersion()
    //取得该扩展的版本
    public ReflectionFunction[] getFunctions()
    //取得该扩展的所有函数
    public array getConstants()
    //取得该扩展的所有常量
    public array getINIEntries()
    //取得与该扩展相关的,在php.ini中的指令信息
    public ReflectionClass[] getClasses()
    public array getClassNames()
}
?>

4。附:

其实从第二点API概览可以看出:接口挺好用的。
一方面Reflector接口为Reflection小系统提供了一个很好的接口命名规范,
每个实现他的类都须按他的规范,从外部看来,这个小系统API很统一。
另一方面由于很多类实现了Reflector接口,
在这样的类层次结构中,若想实现多态是很容易的。



演示用代码如下所示:

<?php
class ClassOne {
function callClassOne() {
print "In Class One";
}
}
class ClassOneDelegator {
private $targets;
function __construct() {
$this->target[] = new ClassOne();
}
function __call($name, $args) {
foreach ($this->target as $obj) {
$r = new ReflectionClass($obj);
if ($method = $r->getMethod($name)) {
if ($method->isPublic() && !$method->isAbstract()) {
return $method->invoke($obj, $args);
}
}
}
}
}
$obj = new ClassOneDelegator();
$obj->callClassOne();
?>

输出结果:
In Class One
可见,通过代理类ClassOneDelegator来代替ClassOne类来实现他的方法
同样的,如下的代码也是能够运行的:

<?php
class ClassOne {
function callClassOne() {
print "In Class One";
}
}
class ClassOneDelegator {
private $targets;
function addObject($obj) {
$this->target[] = $obj;
}
function __call($name, $args) {
foreach ($this->target as $obj) {
$r = new ReflectionClass($obj);
if ($method = $r->getMethod($name)) {
if ($method->isPublic() && !$method->isAbstract()) {
return $method->invoke($obj, $args);
}
}
}
}
}
$obj = new ClassOneDelegator();
$obj->addObject(new ClassOne());
$obj->callClassOne();
?>

PHP反射API--利用反射技术实现的插件系统架构


http://www.e897.com/Article/wlbc/php/200908/5377.html

     1. /**
     2. * @name    PHP反射API--利用反射技术实现的插件系统架构
     3. * @author :PHPCQ.COM
     4. */    
     5. interface Iplugin{    
     6.                 public static function getName();    
     7. }    
     8. function findPlugins(){    
     9.                 $plugins = array();    
    10.                 foreach (get_declared_classes() as $class){    
    11.                                 $reflectionClass = new ReflectionClass($class);    
    12.                                 if ($reflectionClass->implementsInterface('Iplugin')) {    
    13.                                                 $plugins[] = $reflectionClass;    
    14.                                 }    
    15.                 }    
    16.                 return $plugins;    
    17. }    
    18. function computeMenu(){    
    19.                 $menu = array();    
    20.                 foreach (findPlugins() as $plugin){    
    21.                                 if ($plugin->hasMethod('getMenuItems')) {    
    22.                                                 $reflectionMethod = $plugin->getMethod('getMenuItems');    
    23.                                                 if ($reflectionMethod->isStatic()) {    
    24.                                                                 $items = $reflectionMethod->invoke(null);    
    25.                                                 } else {    
    26.                                                                 $pluginInstance = $plugin->newInstance();    
    27.                                                                 $items = $reflectionMethod->invoke($pluginInstance);    
    28.                                                 }    
    29.                                                 $menu = array_merge($menu,$items);    
    30.                                 }    
    31.                 }    
    32.                 return $menu;    
    33. }    
    34. function computeArticles(){    
    35.                 $articles = array();    
    36.                 foreach (findPlugins() as $plugin){    
    37.                                 if ($plugin->hasMethod('getArticles')) {    
    38.                                                 $reflectionMethod = $plugin->getMethod('getArticles');    
    39.                                                 if ($reflectionMethod->isStatic()) {    
    40.                                                                 $items = $reflectionMethod->invoke(null);    
    41.                                                 } else {    
    42.                                                                 $pluginInstance = $plugin->newInstance();    
    43.                                                                 $items = $reflectionMethod->invoke($pluginInstance);    
    44.                                                 }    
    45.                                                 $articles = array_merge($articles,$items);    
    46.                                 }    
    47.                 }    
    48.                 return $articles;    
    49. }    
    50. require_once('plugin.php');    
    51. $menu = computeMenu();    
    52. $articles    = computeArticles();    
    53. print_r($menu);    
    54. print_r($articles);    
    55.    
    56.    
    57. //plugin.php 代码如下    
    58. <?php    
    59. class MycoolPugin implements Iplugin {    
    60.                 public static function getName(){    
    61.                                 return 'MycoolPlugin';    
    62.                 }    
    63.                 public static function getMenuItems(){    
    64.                                 return array(array('description'=>'MycoolPlugin','link'=>'/MyCoolPlugin'));    
    65.                 }    
    66.                 public static function getArticles(){    
    67.                                 return array(array('path'=>'/MycoolPlugin','title'=>'This is a really cool article','text'=>xxxxxxxxx));    
    68.                 }    
    69. }



分享到:
评论

相关推荐

    java反射机制详解

    ### Java反射机制详解 #### 一、反射机制是什么 反射机制是Java编程语言的一个核心特性,它允许程序在运行时动态地获取类的信息,并且能够动态地创建对象和调用对象的方法。简单来说,反射机制使得Java程序可以...

    java 反射机制详解

    Java 反射机制是 Java 语言中的一个重要特性,它允许程序在运行时动态地获取类的信息(如类名、属性、方法等)并调用对象的方法,甚至修改对象的状态。这一机制极大地增强了 Java 程序的灵活性和可扩展性,尤其是在...

    JAVA基础--JAVA中的反射机制详解

    JAVA 反射机制详解 JAVA 反射机制是 Java 语言中的一种动态获取信息和动态调用对象方法的功能。它允许程序在运行时获取类的信息、构造对象、获取成员变量和方法、调用对象的方法等。 Java 反射机制主要提供了以下...

    JAVA反射机制详解视频

    (类的加载概述和加载时机) (类加载器的概述和分类) (获取class文件对象的三种方式) (通过反射获取无参构造方法并使用) (通过反射获取带参构造方法并使用) (通过反射获取私有构造方法并使用) ...(动态代理的概述和实现)

    JAVA反射机制详解

    ### JAVA反射机制详解 #### 一、JAVA反射机制概述 反射是Java编程语言的一个核心特性,它允许程序在运行时获取类的信息,并且可以动态地创建对象和调用方法。这种能力使得Java程序具备了高度的灵活性和扩展性。...

    关于C#的反射机制详解

    反射(Reflection)是.NET中的重要机制,通过放射,可以在运行时获得.NET中每一个类型(包括类、结构、委托、接口和枚举等)的成员,包括方法、属性、事件,以及构造函数等。还可以获得每个成员的名称、限定符和参数...

    java反射机制详解及Method.invoke解释.pdf

    Java 反射机制详解及 Method.invoke 解释 Java 反射机制是 Java 语言中的一种功能,允许程序在运行时访问和修改类、对象、方法、变量等的信息。这种机制提供了许多强大的功能,例如在运行时判断对象所属的类、构造...

    反射机制详解

    反射机制是Java语言中一种强大的机制,它允许程序在运行期间进行自我检查以及操作类、方法、属性等。通过反射,开发者能够在运行时加载、探知并使用编译期间完全未知的类。Java的反射机制为动态性提供了广泛的支持,...

    PHP基于反射机制实现插件的可插拔设计详解

    本篇文章详细介绍如何利用PHP的反射机制实现插件化设计,通过实例来具体分析插件功能的实现、反射机制的原理以及可插拔设计的步骤。 首先,插件化设计通常需要实现一个插件接口,该接口定义了所有插件必须实现的...

    Java 反射机制实例详解

    Java 反射机制实例详解 Java 反射机制实例详解是一种动态语言机制,允许在程序运行时加载、探知和使用编译...Java 反射机制实例详解是一种功能强大且灵活的机制,能够帮助开发者在 Java 程序中实现许多复杂的功能。

    java的反射 发射详解

    4. **插件架构**:反射可以实现动态加载插件的功能。 #### 四、总结 Java的反射机制提供了一种在运行时获取和操作类的能力,这对于构建灵活的应用程序非常重要。然而,反射操作通常比常规的Java代码慢得多,并且...

    java面试题--反射机制

    ### Java反射机制详解 #### 一、引言 在Java面试中,经常会出现与反射机制相关的题目。这是因为Java反射机制不仅是Java语言的一项重要特性,也是理解Java动态特性的关键所在。通过本文,我们将深入探讨Java反射...

    反射机制和类加载机制学习总结

    ### 反射机制详解 #### 一、反射机制概述 反射是Java的一项核心特性,它使得Java程序在运行时能够动态地获取类的信息,并且能够直接操作这些信息。这种能力在许多其他编程语言中并不常见,例如在Pascal、C或C++中...

    详解JAVA 反射机制

    Java 反射机制详解 Java 反射机制是 Java 语言中一个非常强大且灵活的机制,它允许在运行时获取类的信息、创建对象、调用方法和访问成员变量等。反射机制在 Java 中的应用非常广泛,例如在框架中,如 Spring、...

    C++反射机制

    ### C++反射机制详解 #### 引言:C++与反射机制 在现代软件开发领域,反射机制(Reflection)作为一种强大的编程技术,被广泛应用于多种编程语言中,如C#、Java等。它允许程序在运行时检查和修改自身结构与行为,...

    Java 反射机制详解及实例

    Java 反射机制详解及实例 Java 反射机制是 Java 中一种强大的工具,能够使我们很方便的创建灵活的代码,这些代码可以再运行时装配,无需在组件之间进行源代码链接。下面是 Java 反射机制的详细知识点: 一、反射...

    Java 反射机制的实例详解

    想要了解反射首先要理解 Class 类,它是反射实现的基础。Class 是所有类的类(There is a class named Class)。每个类都有一个隐含的静态成员变量 class,这种方式是通过获取类的静态成员变量 class 得到的。 四、...

    详解数据架构的七类视图

    数据架构是IT领域中至关重要的组成部分,它连接着业务需求与技术实现,是构建高效、稳定、可扩展的系统的基础。本文将详细阐述数据架构的七类视图,旨在为数据管理和信息系统建设提供清晰的指引。 首先,企业架构是...

Global site tag (gtag.js) - Google Analytics