代理模式 代理模式

代理模式

1. 代理模式 
    代理模式的作用是:为其他对象提供一种代理以控制对这个对象的访问。在某些情况下,一个客户不想或者不能直接引用另一个对象,而代理对象可以在客户端和目标对象之间起到中介的作用。 
    代理模式一般涉及到三个角色: 
    抽象角色:声明真实对象和代理对象的共同接口; 
    代理角色:代理对象角色内部含有对真实对象的引用,从而可以操作真实对象,同时代理对象提供与真实对象相同的接口以便在任何时刻都能代替真实对象。同时,代理对象可以在执行真实对象操作时,附加其他的操作,相当于对真实对象进行封装。 
     真实角色:代理角色所代表的真实对象,是我们最终要引用的对象。

简单示例代码如下:

 

Java代码    收藏代码
  1. /** 
  2.  *  
  3.  * @功能:代理模式中公共的行为接口 
  4.  * @创建人 gao_jie 
  5.  * @创建日期 May 8, 2009 
  6.  * @版本 1.0 
  7.  *  
  8.  */  
  9. public abstract class Subject {  
  10.     public abstract void request();  
  11. }  
  12. /** 
  13.  *  
  14.  * @功能:代理模式中真正的实现 
  15.  * @创建人 gao_jie 
  16.  * @创建日期 May 8, 2009 
  17.  * @版本 1.0 
  18.  *  
  19.  */  
  20. public class RealSubject extends Subject {    
  21.     /** 
  22.      * 构造函数 
  23.      */  
  24.     public RealSubject(){     
  25.     }  
  26.     /* (non-Javadoc) 
  27.      * @see six.proxytrip.Subject#request() 
  28.      */  
  29.     public void request() {  
  30.         System.out.println("this is a real request!");    
  31.     }  
  32. }  
  33. /** 
  34.  *  
  35.  * @功能:代理类 
  36.  * @创建人 gao_jie 
  37.  * @创建日期 May 8, 2009 
  38.  * @版本 1.0 
  39.  *  
  40.  */  
  41. public class ProxySubject extends Subject {  
  42.   
  43.     /** 
  44.      * 真正使用对象变量 
  45.      */  
  46.     private RealSubject realSubject;  
  47.   
  48.     @Override  
  49.     public void request() {  
  50.         this.preReqeust();// 调用之前  
  51.         if (realSubject == null) {  
  52.             realSubject = new RealSubject();  
  53.         }  
  54.         realSubject.request();  
  55.         this.posReqeust();// 调用之后  
  56.     }  
  57.   
  58.     /** 
  59.      * 代理类之前的准备工作 
  60.      */  
  61.     public void preReqeust() {  
  62.         System.out.println("调用真正对象之前的准备");  
  63.     }  
  64.   
  65.     /** 
  66.      * 代理类之后的处理工作 
  67.      */  
  68.     public void posReqeust() {  
  69.         System.out.println("调用真正对象之后的处理");  
  70.     }  
  71. }  
  72. /** 
  73.  *  
  74.  * @功 能 : 客户端测试代码 
  75.  * @创建人 gao_jie 
  76.  * @创建日期 May 8, 2009 
  77.  * @版本 1.0 
  78.  *  
  79.  */  
  80. public class Client {  
  81.     /** 
  82.      * @param args 
  83.      */  
  84.     public static void main(String[] args) {  
  85.         ProxySubject proxy = new ProxySubject();  
  86.         proxy.request();  
  87.     }  
  88. }  
  89. 测试结果:  
  90. 调用真正对象之前的准备  
  91. this is a real request!  
  92. 调用真正对象之后的处理  

      由以上代码可以看出,客户实际需要调用的是RealSubject类的request()方法,现在用ProxySubject来代理RealSubject类,同样达到目的,同时还封装了其他方法(preRequest(),postRequest()),可以处理一些其他问题。

另外,如果要按照上述的方法使用代理模式,那么真实角色必须是事先已经存在的,并将其作为代理对象的内部属性。但是实际使用时,一个真实角色必须对应一个 代理角色,如果大量使用会导致类的急剧膨胀;此外,如果事先并不知道真实角色,该如何使用代理呢?这个问题可以通过Java的动态代理类来解决。

1. 代理模式 
    代理模式的作用是:为其他对象提供一种代理以控制对这个对象的访问。在某些情况下,一个客户不想或者不能直接引用另一个对象,而代理对象可以在客户端和目标对象之间起到中介的作用。 
    代理模式一般涉及到三个角色: 
    抽象角色:声明真实对象和代理对象的共同接口; 
    代理角色:代理对象角色内部含有对真实对象的引用,从而可以操作真实对象,同时代理对象提供与真实对象相同的接口以便在任何时刻都能代替真实对象。同时,代理对象可以在执行真实对象操作时,附加其他的操作,相当于对真实对象进行封装。 
     真实角色:代理角色所代表的真实对象,是我们最终要引用的对象。

简单示例代码如下:

 

Java代码    收藏代码
  1. /** 
  2.  *  
  3.  * @功能:代理模式中公共的行为接口 
  4.  * @创建人 gao_jie 
  5.  * @创建日期 May 8, 2009 
  6.  * @版本 1.0 
  7.  *  
  8.  */  
  9. public abstract class Subject {  
  10.     public abstract void request();  
  11. }  
  12. /** 
  13.  *  
  14.  * @功能:代理模式中真正的实现 
  15.  * @创建人 gao_jie 
  16.  * @创建日期 May 8, 2009 
  17.  * @版本 1.0 
  18.  *  
  19.  */  
  20. public class RealSubject extends Subject {    
  21.     /** 
  22.      * 构造函数 
  23.      */  
  24.     public RealSubject(){     
  25.     }  
  26.     /* (non-Javadoc) 
  27.      * @see six.proxytrip.Subject#request() 
  28.      */  
  29.     public void request() {  
  30.         System.out.println("this is a real request!");    
  31.     }  
  32. }  
  33. /** 
  34.  *  
  35.  * @功能:代理类 
  36.  * @创建人 gao_jie 
  37.  * @创建日期 May 8, 2009 
  38.  * @版本 1.0 
  39.  *  
  40.  */  
  41. public class ProxySubject extends Subject {  
  42.   
  43.     /** 
  44.      * 真正使用对象变量 
  45.      */  
  46.     private RealSubject realSubject;  
  47.   
  48.     @Override  
  49.     public void request() {  
  50.         this.preReqeust();// 调用之前  
  51.         if (realSubject == null) {  
  52.             realSubject = new RealSubject();  
  53.         }  
  54.         realSubject.request();  
  55.         this.posReqeust();// 调用之后  
  56.     }  
  57.   
  58.     /** 
  59.      * 代理类之前的准备工作 
  60.      */  
  61.     public void preReqeust() {  
  62.         System.out.println("调用真正对象之前的准备");  
  63.     }  
  64.   
  65.     /** 
  66.      * 代理类之后的处理工作 
  67.      */  
  68.     public void posReqeust() {  
  69.         System.out.println("调用真正对象之后的处理");  
  70.     }  
  71. }  
  72. /** 
  73.  *  
  74.  * @功 能 : 客户端测试代码 
  75.  * @创建人 gao_jie 
  76.  * @创建日期 May 8, 2009 
  77.  * @版本 1.0 
  78.  *  
  79.  */  
  80. public class Client {  
  81.     /** 
  82.      * @param args 
  83.      */  
  84.     public static void main(String[] args) {  
  85.         ProxySubject proxy = new ProxySubject();  
  86.         proxy.request();  
  87.     }  
  88. }  
  89. 测试结果:  
  90. 调用真正对象之前的准备  
  91. this is a real request!  
  92. 调用真正对象之后的处理  

      由以上代码可以看出,客户实际需要调用的是RealSubject类的request()方法,现在用ProxySubject来代理RealSubject类,同样达到目的,同时还封装了其他方法(preRequest(),postRequest()),可以处理一些其他问题。

另外,如果要按照上述的方法使用代理模式,那么真实角色必须是事先已经存在的,并将其作为代理对象的内部属性。但是实际使用时,一个真实角色必须对应一个 代理角色,如果大量使用会导致类的急剧膨胀;此外,如果事先并不知道真实角色,该如何使用代理呢?这个问题可以通过Java的动态代理类来解决。

猜你喜欢

转载自rongdmmap-126-com.iteye.com/blog/1433248
今日推荐