一天一种设计模式之五-----代理模式
2019独角兽企业重金招聘Python工程师标准>>>
一.代理模式简介
代理模式属于结构型模式
定义:代理模式为其他对象提供一种代理以控制对这个对象的访问。
代理模式是java框架层面应用最广泛的少数几种设计模式之一,非常重要。
适用场景:
远程代理,为一个对象在不同的地址空间提供局部代表,这样可以隐藏一个对象存在于不同地址空间的事实。
虚拟代理,根据需要创建开销很大的对象,通过它来存放实例化需要很长时间的对象,这样可以达到性能优化;
安全代理,用来控制真实对象访问时的权限。一般用于对象应该有不同的访问权限的时候;
智能指引,是指当调用真实的对象的时候,代理处理另外的一些事情(用的比较多)
代理模式要求代理实现与被代理对象相同的接口(cglib与被代理对象是子类与父类的关系),以保证任何时候都能代替真实对象。这也是它与适配器模式的区别!!
代理模式广泛应用于aop编程。能够在不改变源代码的前提下提供统一的日志管理,前后置拦截器,符合开放封闭原则、依赖倒置原则,
二.测试代码
下面代码属于静态代理,大致场景是追求者会追妹子,但他不认识某girl,而通过代理类认识,所以追求者通过代理类对妹子展开了追求。
public class ProxyTest {public static void main(String[] args) {PursuitWay pursuitWay=new Proxy(new Pursuiter(new Girl("小白")));pursuitWay.giveFlower();pursuitWay.giveGift();} } interface PursuitWay{void giveFlower();void giveGift(); } class Girl{private String name;public Girl(String name) {this.name=name;}public String getName() {return name;}public void setName(String name) {this.name = name;}} class Pursuiter implements PursuitWay{Girl girl;public Pursuiter(Girl girl){this.girl=girl;}@Overridepublic void giveFlower() {System.out.println("追求者送"+girl.getName()+"花");}@Overridepublic void giveGift() {System.out.println("追求者送"+girl.getName()+"礼物");}}class Proxy implements PursuitWay{PursuitWay pursuter;public Proxy(PursuitWay pursuiter){this.pursuter=pursuiter;}@Overridepublic void giveFlower() {pursuter.giveFlower();}@Overridepublic void giveGift() {pursuter.giveGift();}}
既然是通过代理去追妹子,那每次苦力活代理做做日志,设置个障碍就不难理解了吧。
上述功能如果要通过适配器模式实现,则proxy不必非要实现PursuitWay,它会有自己的方法而不必非要是giveXXX,只需要在它自己的方法中实现pursuter的giveXXX方法就可以了,具体代码略。
上述代理模式属于静态代理,因为代理类是我们自己编写出来的,而动态代理则是通过java虚拟机,在运行期间生成的字节码。
下述代码是通过动态代理实现的相同功能
1. 获取追求者上的所有接口列表;
2. 确定要生成的代理类的类名,默认为:com.sun.proxy.$ProxyXXXX ;3. 根据需要实现的接口信息,在代码中动态创建 该Proxy类的字节码;
4 . 将对应的字节码转换为对应的class 对象;
5. 创建InvocationHandler 实例handler,用来处理Proxy所有方法调用;
6. Proxy 的class对象 以创建的handler对象为参数,实例化一个proxy对象
public class ProxyTest {public static void main(String[] args) {Class clazz=Proxy.getProxyClass(Pursuiter.class.getClassLoader(), Pursuiter.class.getInterfaces());System.out.println("proxy类为"+clazz.getName());System.out.println("proxy实现的接口有"+clazz.getInterfaces()[0].getName());System.out.println("-----开始生成代理对象(实际上该代理对象就是一个该接口的实现类)");PursuitWay pursuter=(PursuitWay) Proxy.newProxyInstance(Pursuiter.class.getClassLoader(), Pursuiter.class.getInterfaces(), new MyInvocationHandler(new Pursuiter(new Girl("小白"))));pursuter.giveFlower();pursuter.giveGift();} } interface PursuitWay{void giveFlower();void giveGift(); } class Girl{private String name;public Girl(String name) {this.name=name;}public String getName() {return name;}public void setName(String name) {this.name = name;}} class Pursuiter implements PursuitWay{Girl girl;public Pursuiter(Girl girl){this.girl=girl;}@Overridepublic void giveFlower() {System.out.println("追求者送"+girl.getName()+"花");}@Overridepublic void giveGift() {System.out.println("追求者送"+girl.getName()+"礼物");}} class MyInvocationHandler implements InvocationHandler{Object object;public MyInvocationHandler(Object object){this.object=object;}@Overridepublic Object invoke(Object proxy, Method method, Object[] args)throws Throwable {return method.invoke(object, args);}}
上述代码通过jdk自带的代理类实现,它和静态代理类有同样的局限性,就是要求被代理类必须有一个或者多个对应具体业务逻辑的接口。myInvocationHandler里边的invoke方法中可以提供拦截、写日志等功能。
cglib包的代理类CglibProxy是针对某个类生成一个子类,该子类自然会包括其父类的所有业务逻辑方法。而且不在局限于必须有上层接口。但是cglib包也要求被代理类不能为final类,否则继承不了,测试代码和动态代理很像,略。
cglib底层采用ASM字节码生成框架,使用字节码技术生成代理类,理论上比使用Java反射效率要高,不过有大神曾经测试过,貌似性能差不多,而且jdk的动态代理还要比cglib效率高一点点。有兴趣的朋友可以去试试。
欢迎大神交流意见。
下一节将会讲解工厂方法模式,该模式在service层应用很普遍。敬请期待。
转载于:https://my.oschina.net/u/2323537/blog/634874
一天一种设计模式之五-----代理模式相关推荐
- java23种设计模式之五:代理模式
一.代理模式介绍 代理模式的定义:就是为一个接品(对象)提供一个代理的对象,并由这个代理对象控制对原对象的访问流程 其中代理又分为:静态代理和动态代理 静态代理:指的是自己要写一个代理类,或者用工具生 ...
- 23种设计模式7_代理模式之一静态代理
23种设计模式7_代理模式之一静态代理 1 基本介绍 代理模式:为其他对象提供一种代理以控制对这个对象的访问 代理模式也叫委托模式,它是一项基本设计技巧.许多其他的模式,如状态模式.策略模式.访问者模 ...
- 带你认识4种设计模式:代理模式、装饰模式、外观模式和享元模式
摘要:本文我们主要介绍结构型模式中的代理模式.装饰模式.外观模式和享元模式. 本文分享自华为云社区<快来,这里有23种设计模式的Go语言实现(三)>,原文作者:元闰子 . 设计模式(Des ...
- 23种设计模式之代理模式
文章目录 代理模式的定义与特点 代理模式的结构与实现 模式的结构 模式的实现 代理模式的应用场景 代理模式的应用实例 代理模式的扩展 代理模式分类 静态代理 动态代理 在有些情况下,一个客户不能或者不 ...
- 在王者荣耀角度下分析面向对象程序设计B中23种设计模式之代理模式
· 代理模式在王者荣耀中的应用 · 应用一(虚拟代理模式) 应用二(远程代理模式) 应用三(充值送好礼) 一.简述 应用一: 在王者荣耀这款游戏里,设置有很多种娱乐游戏模式,比如:无限乱斗.梦境大乱斗 ...
- 23种设计模式之代理模式(动态代理)
代理模式 代理模式的定义:为其他对象提供一种代理以控制对这个对象的访问.在某些情况下,一个对象不适合或者不能直接引用另一个对象,而代理对象可以在客户端和目标对象之间起到中介的作用. 代理模式的组成 抽 ...
- 二十四种设计模式:代理模式(Proxy Pattern)
代理模式(Proxy Pattern) 介绍 为其他对象提供一个代理以控制对这个对象的访问. 示例 有一个Message实体类,某对象对它的操作有Insert()和Get()方法,用一个代理来控制对这 ...
- 23三种设计模式之代理模式
一.概念 通过代理对象访问目标对象.这样做的好处是:可以在目标对象实现的基础上,增强额外的功能操作,即扩展目标对象的功能. 代理模式的关键点是:代理对象与目标对象.代理对象是对目标对象的扩展,并会调用 ...
- 二十四种设计模式之代理模式
一.什么是代理模式? 简单来说,代理模式就相当于我们生活中的中介,比如我们租房子通过房产中介或者是租房的app,买电影票通过app,就是我们实现事情的一个媒介. 二.代理模式实例 1.就比如说,程序员 ...
最新文章
- Selenium + Nightwatch 自动化测试环境搭建
- 跟着iMX28x开发套件学linux-02
- 深入iOS系统底层之CPU寄存器介绍
- 次小生成树(POJ1679/CDOJ1959)
- 26.Android Studio下Ndk开发(ffmpeg导入Android studio以cmake方式编译的过程)
- 你见过哪些操蛋的代码?
- ES5和ES6类的知识
- Python学习札记(八) Basic5 循环
- DNS使用的是TCP协议还是UDP协议
- 什么是智能标签?DevExpress WPF控件这份入门指南请查收
- Windows系统重装Linux系统
- 【Python】turtle安装报错ERROR: Command errored out with exit status 1
- Unity 增加2D游戏的打击感笔记
- TTS交易所的STO(证券化通证)、资产证券化(ABS)与ICO之间的区别
- opencv-python图片的镜像
- Clion源码编辑器的学习与实践
- Android多语言设置
- android应用间相互调用
- Unity中EnableDisableComponent的用法
- C/C++是程序员必须掌握的语言吗?