设计模式(十二):代理模式

200 阅读1分钟

介绍

在代理模式(Proxy Pattern)属于结构型模式。用一个类代表另一个类的功能。我们创建具有现有对象的对象,以便向外界提供功能接口。

优点

  • 职责清晰
  • 高扩展性
  • 智能化

缺点

  • 实现复杂
  • 处理会变慢

应用

Android中的IPC机制、Retrofit、还有AppcompatActivity中view的遍历替换都采用了代理模式

实现

关键代码:实现同一接口,创建具有现有对象的对象,以便向外界提供功能接口(添加中间层)

 interface Client {
    void pay();
 }

 class RealClient implements Client {
 
    private GoodsType goodtype;
  
    // 在构造时进行find(),代理类直接帮忙寻找,隐藏细节
    public RealClient(GoodsType goods){
       this.goodtype = goods;
       find();
    }

    @Override
    public void pay() {
       System.out.println("pay for " + goodtype);
    }

    private void find(){
       System.out.println("Find " + goodtype);
    }
 }

 class Proxy implements Client {

    RealClient realClient;

    public GoodsType goodtype;
 
    public Proxy(RealClient realClient){
        this.realClient = realClient; //这里是关键啦
    }
   
    // 客户进行支付
    @Override
    public void pay() {
       realClient.pay();
    }
 }

 enum GoodsType{
    HOUSE,CAR
 }

 class ProxyPatternDemo {

    public static void main(String[] args) {
    
       Client client = new Proxy(new RealClient(GoodsType.HOUSE));
  
       client.pay();
       System.out.println("---租期到后,直接续租---");
       client.pay();
    }
 }

运行结果:

Find HOUSE
pay for HOUSE
---租期到后,直接续租---
pay for HOUSE

动态代理:

import java.lang.reflect.InvocationHandler;
import java.lang.reflect.Method;
import java.lang.reflect.Proxy;

interface UserService {
    void select();
    void update();
}

class UserServiceImpl implements UserService {
    @Override
    public void select() {
      System.out.println("查询");
    }
  
    @Override
    public void update() {
      System.out.println("更新");
    }
}
  
  

class ProxyHandler implements InvocationHandler {

    private final Object target; // 被代理对象
  
    public ProxyHandler(Object target) {
      this.target = target;
    }
  
    @Override
    public Object invoke(Object proxy, Method method, Object[] args) 
      throws Throwable {
      before();
      // 调用 target 的 method 方法
      Object result = method.invoke(target, args);
      after();
      return result;
    }
  
    private void before() {
      System.out.println("动态代理-----方法执行前");
    }
  
    private void after() {
      System.out.println("动态代理-----方法执行后");
    }
}
  

class a{
    public static void main(String[] args){
        UserService userService = new UserServiceImpl();
        ClassLoader classLoader = userService.getClass().getClassLoader();
        Class<?>[] interfaces = userService.getClass().getInterfaces();
        ProxyHandler proxyHandler = new ProxyHandler(userService);
        UserService proxy = (UserService) Proxy.newProxyInstance(classLoader, interfaces, proxyHandler);
        proxy.select();
    }
}
动态代理-----方法执行前
查询
动态代理-----方法执行后