前往小程序,Get更优阅读体验!
立即前往
首页
学习
活动
专区
工具
TVP
发布
社区首页 >专栏 >【设计模式-代理模式】

【设计模式-代理模式】

作者头像
Liusy
发布2020-09-01 16:25:00
1880
发布2020-09-01 16:25:00
举报
文章被收录于专栏:Liusy01

【导读】很多场景需要一个中介去完成,例如租房,找工作等。中介会帮你去完成一些其他操作,比如准备合同、与第三方对接等等。此时就需要用到代理模式。

其实Java的动态代理以及spring的CGLib就是用的此模式。

一、定义

为其他对象提供一种代理,以控制对这个对象的访问。比如某些对象的创建比较耗时,就可以使用代理,也可以使用享元模式。

二、实例

有两种方式,一种是静态代理,一种是动态代理。

(1)静态代理

说白了就是在方法执行前后生硬的加上其它处理逻辑。就类似下列代码,在订单保存的前后进行相应的逻辑处理。

代码语言:javascript
复制
public class StaticOrderProxy {

    private OrderService orderService;

    public StaticOrderProxy(OrderService orderService) {
        this.orderService = orderService;
    }

    public int saveOrder(Order order) {
        System.out.println("保存订单之前的处理逻辑");
        int orderId = orderService.saveOrder(order);
        System.out.println("保存订单之后的处理逻辑");
        return orderId;
    }
}

静态代理不适合开闭原则,基本没有扩展性。

(2)动态代理

以JDK的动态代理为例,其代理的类是需要继承接口的,否则会报错。

之前专门有一篇【JDK动态代理源码分析】,感兴趣的可以看一下。

1、必须要有一个类实现InvocationHandler接口

代码语言:javascript
复制
public class DynamicOrderProxy implements InvocationHandler {

    Object target;

    public DynamicOrderProxy(Object target) {
        this.target = target;
    }


    //生成代理类 
    public Object bind(){
        Class<?> aClass = target.getClass();
        return Proxy.newProxyInstance(aClass.getClassLoader(),aClass.getInterfaces(),this);
    }
    /**
     * @param proxy 动态代理实例
     * @param method 需要执行的方法
     * @param args 方法中参数
     * @return
     * @throws Throwable
     */
    @Override
    public Object invoke(Object proxy, Method method, Object[] args) throws Throwable {
        System.out.println("保存订单之前的逻辑");
        Object result = method.invoke(target, args);
        System.out.println("保存订单之前的逻辑");
        return result;
    }
}

2、需要代理的类

代码语言:javascript
复制
1、接口
public interface OrderService {

    int saveOrder(Order order);

    void test(String a);
}

2、实现类,需要代理的类
public class OrderServiceImpl implements OrderService {

    private OrderDao orderDao ;

    public OrderServiceImpl() {
    }

    public OrderServiceImpl(OrderDao orderDao) {
        this.orderDao = orderDao;
    }

    @Override
    public int saveOrder(Order order) {
        orderDao = new OrderDaoImpl();
        return orderDao.saveOrder(order);
    }
}

3、测试类

代码语言:javascript
复制
OrderService orderService = (OrderService) new DynamicOrderProxy(new OrderServiceImpl()).bind();
Order order = new Order();
order.setOrderId("测试订单号");
orderService.saveOrder(order);

运行结果:

代理模式比较简单。

三、源码实例

(1)JDK动态代理

(2)Spring的AOP

本文参与 腾讯云自媒体同步曝光计划,分享自微信公众号。
原始发表:2020-03-20,如有侵权请联系 cloudcommunity@tencent.com 删除

本文分享自 Liusy01 微信公众号,前往查看

如有侵权,请联系 cloudcommunity@tencent.com 删除。

本文参与 腾讯云自媒体同步曝光计划  ,欢迎热爱写作的你一起参与!

评论
登录后参与评论
0 条评论
热度
最新
推荐阅读
领券
问题归档专栏文章快讯文章归档关键词归档开发者手册归档开发者手册 Section 归档