代理模式

代理模式:Proxy

1、基本原理

代理模式的定义:对其他对象提供一种代理以控制对这个对象的访问。

代理模式的思想是为了提供额外的处理或者不同的操作而在实际对象与调用者之间插入一个代理对象。这些额外的操作通常需要与实际对象进行通信。

 

代理模式一般涉及到的角色

l 抽象角色:真实对象和代理对象的共同接口

l 真实角色:真实对象,最终要引用的对象

l 代理角色

n 内部含有对真实对象的引用,从而可以操作真实对象

n 提供与真实对象相同的接口以便在任何时刻代替真实对象

n 可在执行真实对象操作前后附加其他操作,相当于对真实对象进行封装

代理模式 

代理模式包括静态代理和动态代理两种实现

 

Java动态代理类位于Java.lang.reflect包下,一般主要涉及到以下两个类:

l Interface InvocationHandler:该接口中仅定义了一个方法Object:invoke(Object obj,Method method, Object[] args)。在实际使用时,第一个参数obj一般是指代理类,method是被代理的方法,args为该方法的参数数组。这个抽象方法在代理类中动态实现。

l Proxy:该类即为动态代理类,其中主要包含以下内容:

n Protected Proxy(InvocationHandler h):构造函数,给内部h赋值

n Static Class getProxyClass(ClassLoader loader,Class[] interfaces):获得一个代理类,其中loader是类装载器,interfaces是真实类所拥有的全部接口的数组

n Static Object newProxyInstance(ClassLoader loader, Class[] interfaces, InvocationHandler h):返回代理类的一个实例。

2、优缺点

 优点

 不需要修改目标对象就实现了功能的增加

 缺点(静态代理)

 真实角色必须是事先已经存在的,并将其作为代理对象的内部属性。如果事先并不知道真实角色则无法使用

 一个接口(或者一个真实角色)必须对应一个代理角色,大量使用会导致类的急剧膨胀

 静态代理和动态代理的比较

 静态代理类确实存在,动态代理类在运行期动态生成

 一个真实角色必须对应一个静态代理角色,而动态代理大大减少了代理类的数量

 动态代理类不会作实质性的工作,在生成它的实例时必须提供一个handler,由它接管实际的工作(会自动执行handler的invoke方法)

3、适用情况

代理模式的主要作用是为其他对象提供一种代理以控制对这个对象的访问。在某些情况下,一个对象不想或者不能直接引用另一个对象,而代理对象可以在客户端和目标对象之间起到中介的作用。

4、应用举例

1、使用代理实现Hibernate中的延迟加载:

Hibernate 的延迟加载本质上就是代理模式的应用,我们经常通过代理模式来降低系统的内存开销、提升应用的运行性能。Hibernate 充分利用了代理模式的这种优势,并结合了 Javassist 或 CGLIB 来动态地生成代理对象,这更加增加了代理模式的灵活性,Hibernate 给这种用法一个新名称:延迟加载。

Hibernate 是通过代理模式来“推迟”加载关联实体的时间,如果程序并不需要访问关联实体,那程序就不会去抓取关联实体了,这样既可以节省系统的内存开销,也可以缩短 Hibernate 加载实体的时间。

2、使用动态代理实现Spring的AOP功能

如果目标对象实现了接口,默认情况下会采用JDK的动态代理实现AOP;如果目标对象实现了接口,可以强制使用CGLIB实现AOP;如果目标对象没有实现了接口,必须采用CGLIB库,spring会自动在JDK动态代理和CGLIB之间转换

5、其他

根据《Java与模式》书中对代理模式的分类,代理模式分为8种,将几种常见的、重要的列举如下:
1. 远程(Remote)代理:为一个位于不同的地址空间的对象提供一个局域代表对象。比如:你可以将一个在世界某个角落一台机器通过代理假象成你局域网中的一部分。
2. 虚拟(Virtual)代理:根据需要将一个资源消耗很大或者比较复杂的对象延迟的真正需要时才创建。比如:如果一个很大的图片,需要花费很长时间才能显示出来,那么当这个图片包含在文档中时,使用编辑器或浏览器打开这个文档,这个大图片可能就影响了文档的阅读,这时需要做个图片Proxy(留出一个方框、或者是显示进度条、或者是显示一个小图片))来代替真正的图片。
3. 保护(Protect or Access)代理:控制对一个对象的访问权限。比如:在论坛中,不同的身份登陆,拥有的权限是不同的,使用代理模式可以控制权限(当然,使用别的方式也可以实现)。
4. 智能引用(Smart Reference)代理:提供比对目标对象额外的服务。比如:纪录访问的流量(这是个再简单不过的例子),提供一些友情提示等等。