设计模式——代理模式

8.代理模式

代理模式跟装饰器模式好像,只不过设计目的不同。

静态代理

下面这个例子来自——菜鸟教程

public interface Image {
   void display();
}
public class RealImage implements Image {
 
   private String fileName;
 
   public RealImage(String fileName){
      this.fileName = fileName;
      loadFromDisk(fileName);
   }
 
   @Override
   public void display() {
      System.out.println("Displaying " + fileName);
   }
 
   private void loadFromDisk(String fileName){
      System.out.println("Loading " + fileName);
   }
}
public class ProxyImage implements Image{
 
   private RealImage realImage;
   private String fileName;
 
   public ProxyImage(String fileName){
      this.fileName = fileName;
   }
 
   @Override
   public void display() {
      if(realImage == null){
         realImage = new RealImage(fileName);
      }
      realImage.display();
   }
}
public class ProxyPatternDemo {
   
   public static void main(String[] args) {
      Image image = new ProxyImage("test_10mb.jpg");
 
      // 图像将从磁盘加载
      image.display(); 
      System.out.println("");
      // 图像不需要从磁盘加载
      image.display();  
   }
}

看到这儿看起来很眼熟对吧,这个实现上跟装饰器模式几乎没区别把。

装饰器是为了增加新的功能或者删除已有的功能而实现的,这些功能与目标功能类似,比如宝马汽车可以飞。代理模式则是把任务交给建立的对象来做,实现一些不同的功能,比如增加日志。

输出

Loading test_10mb.jpg
Displaying test_10mb.jpg

Displaying test_10mb.jpg

以上说的是静态代理。

那为啥叫静态代理呢?咱们看看动态代理。

动态代理

所谓的动态代理就是在程序运行中,动态的建立代理类。

看以下例子

public interface Image {
    void display();
}
public class RealImage implements Image {
    private String fileName;

    public RealImage(String fileName){
        this.fileName = fileName;
        loadFromDisk(fileName);
    }

    @Override
    public void display() {
        System.out.println("Displaying " + fileName);
    }

    private void loadFromDisk(String fileName){
        System.out.println("Loading " + fileName);
    }
}
import java.lang.reflect.InvocationHandler;
import java.lang.reflect.Method;

public class ImageInovationHandler implements InvocationHandler {

    private RealImage realImage;

    public ImageInovationHandler(RealImage realImage) {
        this.realImage = realImage;
    }

    @Override
    public Object invoke(Object proxy, Method method, Object[] args) throws Throwable {
		//添加处理日志啊啥的
        //System.out.println();
        method.invoke(realImage,args);
        return null;
    }
}
public class Client {

    public static void main(String[] args) {
        RealImage realImage = new RealImage("test_10mb.jpg");
        InvocationHandler imageInvocationHandler = new ImageInovationHandler( realImage);
        //通过反射得到RealImage的代理对象
        Image realImageProxy = (Image) Proxy.newProxyInstance(realImage.getClass().getClassLoader(), realImage.getClass().getInterfaces(), imageInvocationHandler);
        //调用display方法
        realImageProxy.display();
    }
}

动态代理使用了java自带的接口和类。

把所有的代理类都交给InvocationHandler的实现类处理。Proxy通过反射,动态地建立代理对象,调用所需要调用的方法。

所谓的动态代理就是在程序运行中,动态的建立代理类。

可以看出,如果使用静态代理,给每个想代理的对象都增加日志功能,那么就需要给每个想要被代理的对象书写代理类,而动态代理 ,只需要写一个代理类,就可以给每个想代理增加日志功能。

评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值