从代理设计模式到Spring AOP
例子场景:打架
如:
桃花岛比武抢亲之战 —— 郭靖与欧阳克
华山论剑正邪之战 —— 北丐洪七公和西毒欧阳峰
小朋友梦想之战 —— 奥特曼与铠甲勇士
…
这些战斗之中,都要打架,但是打架之前需要有一些前期准备,打架(实战)工作由目标对象实现,而前期的准备(练功)工作则由代理对象实现。
静态代理实现方式一
真实打架行为接口:
public interface IRealFight{void fight();
}
抢亲之战:
public class QiangQinFightImpl implements IRealFight{@Overridepublic void fight(){System.out.println("郭靖和欧阳克战斗!");}
}
正邪之战:
public class GoodEvilFightImpl implements IRealFight{@Overridepublic void fight(){System.out.println("北丐洪七公和西毒欧阳锋战斗!");}
}
梦想之战
public class DreamFightImpl implements IRealFight{@Overridepublic void fight(){System.out.println("奥特曼和铠甲勇士战斗!");}
}
真实战斗代理类
以上的战斗都需要提前练功,练功的准备由代理类实现
public class ProxyVirtualFight implements IRealFight{//需要给我一个目标对象private IRealFight targetFigth;//给了我一个目标对象public ProxyVirtualFight(IRealFight targetFight){this.targetFight = targetFight;}/*** 我来负责全程打架,包括前期练功和实际战斗*/@Overridepublic void fight(){//前期练功System.out.println("战斗双方正在练功,请不要打扰我们!!!");//实际战斗开始targetFigth.fight();//战斗结束System.out.println("这场战斗结束了.");}
}
观众需求:
观众想要看他们自己想要的任意一场战斗
public class Client{public static void main(String[] args){//=====广场大妈,我们想要看【抢亲之战】=====//1.战斗对象准备好了QiangQinFightImpl qiangQin = new QiangQinFightImpl();//2.代理对象也准备好了ProxyVirtualFight proxy1 = new ProxyVirtualFight(qiangQin);//3.开始战斗proxy1.fight();//=====二B青年,我们想要看【正邪之战】=====//1.战斗对象准备好了GoodEvilFightImpl goodEvil = new GoodEvilFightImpl();//2.代理对象也准备好了ProxyVirtualFight proxy2 = new ProxyVirtualFight(goodEvil);//3.开始战斗proxy2.fight(); //=====祖国花朵,我们想要看【梦想之战】=====//1.战斗对象准备好了DreamFightImpl dream = new DreamFightImpl();//2.代理对象也准备好了ProxyVirtualFight proxy3 = new ProxyVirtualFight(dream);//3.开始战斗proxy3.fight(); }
}
静态代理实现方式二
结合简单工厂模式
有观众骂起来了,要自己去创建各种战斗对象,好烦啊。
建个工厂类,给你们(观众)创建战斗对象
public class FightFactory{//亲爱观众,你们自己实现吧,简单工厂、工厂方法、抽象工厂,自己用去。。//算了,还是帮你们创建吧(简单工厂)public static IRealFight createFight(String fightName){if("QiangQin".equals(fightName)){return new QiangQinFightImpl();}else if("GoodEvil".equals(fightName)){return new GoodEvilFightImpl();}else if("Dream".equals(fightName)){return new DreamFightImpl();}}
}
现在的观众:
public class Client{public static void main(String[] args){//=====广场大妈,我们想要看【抢亲之战】=====//1.战斗对象准备好了IRealFight qiangQin = FightFactory.createFight("QiangQin");//2.代理对象也准备好了ProxyVirtualFight proxy1 = new ProxyVirtualFight(qiangQin);//3.开始战斗proxy1.fight();//=====二B青年,我们想要看【正邪之战】=====//1.战斗对象准备好了IRealFight goodEvil = FightFactory.createFight("GoodEvil");//2.代理对象也准备好了ProxyVirtualFight proxy2 = new ProxyVirtualFight(goodEvil);//3.开始战斗proxy2.fight(); //=====祖国花朵,我们想要看【梦想之战】=====//1.战斗对象准备好了IRealFight dream = FightFactory.createFight("Dream");//2.代理对象也准备好了ProxyVirtualFight proxy3 = new ProxyVirtualFight(dream);//3.开始战斗proxy3.fight(); }
}
静态代理实现方式三
结合工厂方法模式
有观众第二次开始骂起来了,我们哪里记得那么多的名称啊,好烦啊。
建另外一种工厂类,给你们(观众)创建战斗对象
public class FightFactory{//工厂方法public static IRealFight createQiangQin(){return new QiangQinFightImpl();}public static IRealFight createGoodEvil(){return new GoodEvilFightImpl();}public static IRealFight createDream(){return new DreamFightImpl();}
}
现在的观众:
public class Client{public static void main(String[] args){//=====广场大妈,我们想要看【抢亲之战】=====//1.战斗对象准备好了QiangQinFightImpl qiangQin = FightFactory.createQiangQin();//2.代理对象也准备好了ProxyVirtualFight proxy1 = new ProxyVirtualFight(qiangQin);//3.开始战斗proxy1.fight();//=====二B青年,我们想要看【正邪之战】=====//1.战斗对象准备好了GoodEvilFightImpl goodEvil = FightFactory.createGoodEvil();//2.代理对象也准备好了ProxyVirtualFight proxy2 = new ProxyVirtualFight(goodEvil);//3.开始战斗proxy2.fight(); //=====祖国花朵,我们想要看【梦想之战】=====//1.战斗对象准备好了DreamFightImpl dream = FightFactory.createDream();//2.代理对象也准备好了ProxyVirtualFight proxy3 = new ProxyVirtualFight(dream);//3.开始战斗proxy3.fight(); }
}
静态代理实现方式四
结合抽象工厂模式
有观众第三次又开始骂起来了,这实现跟之前的差不了多少,神经病啊。
建另外一种工厂类
public class FightFactory{//工厂方法public static IRealFight createQiangQin(){return new QiangQinFightImpl();}public static IRealFight createGoodEvil(){return new GoodEvilFightImpl();}public static IRealFight createDream(){return new DreamFightImpl();}
}
现在的观众:
public class Client{public static void main(String[] args){//=====广场大妈,我们想要看【抢亲之战】=====//1.战斗对象准备好了QiangQinFightImpl qiangQin = FightFactory.createQiangQin();//2.代理对象也准备好了ProxyVirtualFight proxy1 = new ProxyVirtualFight(qiangQin);//3.开始战斗proxy1.fight();//=====二B青年,我们想要看【正邪之战】=====//1.战斗对象准备好了GoodEvilFightImpl goodEvil = FightFactory.createGoodEvil();//2.代理对象也准备好了ProxyVirtualFight proxy2 = new ProxyVirtualFight(goodEvil);//3.开始战斗proxy2.fight(); //=====祖国花朵,我们想要看【梦想之战】=====//1.战斗对象准备好了DreamFightImpl dream = FightFactory.createDream();//2.代理对象也准备好了ProxyVirtualFight proxy3 = new ProxyVirtualFight(dream);//3.开始战斗proxy3.fight(); }
}
//客户是上帝,但是观众不是可不是上帝。。。离主题有点远了。。。回归代理了。
哇哈哈哈,打架不仅是真实的打架,还有虚拟的打架哦。虚拟打架也要有相同的练功前期工作哦
如:
拳皇
魂斗罗
虚拟打架接口
public interface IVirtualFight{void fight();
}
拳皇
public class QuanHuangFight implements IVirtualFight{@Overridepublic void fight(){System.out.println("拳皇二阶堂红丸打草薙京");}
}
魂斗罗
public class HunDouLuoFight implements IVirtualFight{@Overridepublic void fight(){System.out.println("魂斗罗打啊打啊打啊。。");}
}
这虚拟打架前也需要练功吗???虽然不练功,但是也有前奏,额外的工作由代理对象来完成。根据前面的方法,也需要有相应代理类
虚拟打架代理类
public class ProxyVirtualFight implements IVirtualFight{//给我一个虚拟打架对象private IVirtualFight virtualFight;//给了一个虚拟对象public ProxyVirtualFight(IVirtualFight virtualFight){this.virtualFight = virtualFight;}@Overridepublic void fight(){前期练功System.out.println("战斗双方正在练功,请不要打扰我们!!!");//战斗virtualFight.fight();//虚拟战斗结束System.out.println("这场战斗结束了.");}
}
问题来了没啊。。默默的又多了一个代理类,而且这个代理类的代理业务逻辑和之前的代理类是一样的。好啰嗦啊。。。
我想要的是只要一个代理类来完成真实打架和虚拟打架中前期练功的工作就好!!!!!!
传说中的动态代理可以帮你完成的哦。瞧瞧以下的办法
动态代理
jdk实现动态代理
用jdk实现动态代理,需要继承一个接口InvocationHandler
代理处理类
public class ProxyFight implements InvocationHandler{//给我一个目标对象(是真实打架或者虚拟打架对象)private Object target;//给了你一个目标对象了public ProxyFight(Object target){this.target = target;}//绑定委托对象并返回一个代理类public Object bind(Object target){this.target = target;return Proxy.newProxyInstance(target.getClass.getClassLoader(),target.getClass().getInterfaces(),this);}@Overridepublic Object invoke(Object proxy, Method method, Object[] args)throws Throwable{前期练功System.out.println("战斗双方正在练功,请不要打扰我们!!!");//战斗method.invoke(target,args);//虚拟战斗结束System.out.println("这场战斗结束了.");}}
观众要来了,战斗越来越多,现在有真实战斗如:抢亲之战、正邪之战、梦想之战;还有虚拟战斗游戏如:魂斗罗、拳皇。。。哈哈哈,有意思。
public class Client{public static void main(String[] args){//广场大妈想看【抢亲之战】ProxyFight proxy = new ProxyFight();IRealFight real = (IRealFight)proxy.bind(new QiangQinFightImpl());real.fight();}
}
看看jdk动态代理实现过程有点傻眼,一脸懵逼样子,不知道啥跟啥个啥。。。
Dynamic Proxy机制:可以为指定的接口在系统运行期间动态的生成代理对象。
需要一个接口和一个类,java.lang.reflect.Proxy类和java.lang.reflection.InvocationHandler接口。动态代理虽好,但是不能满足所有的需求。因为动态代理机制只能实现了相应接口的类使用。
Proxy.newProxyInstance(target.getClass.getClassLoader(),target.getClass().getInterfaces(),this)
这个实例化了一个代理类,好屌的样子,这里面的第二个参数,目标类实现的接口类,即我的目标类必须要继承xxx接口,不然就没法创建对象了哦。
如果目标类没有实现一个接口,那怎么办了?
那就看看不知道哪位大师搞出来的CGLIB动态代理了吧。
CGLIB实现动态代理
CGLIB是开源的动态字节码生成类库,为目标对象生成动态的代理对象实例。
大师对它的原理是这么说的:
对目标对象进行继承扩展,为其生成相应的子类,而子类可以通过覆写来扩展父类的行为,只要将横切逻辑的实现放到子类中,然后然系统使用扩展后的目标对象的子类,就可以达到与代理模式相同的效果了。
SubClass instanceof SuperClass == true.
需要的材料
net.sf.cglib.proxy.Callbacknet.sf.cglib.proxy.MethodInterceptor(继承了Callback)
从新准备一下代码喽
抢亲之战
public class QiangQinFightImpl{public void fight(){System.out.println("郭靖和欧阳克战斗!");}
}
正邪之战
public class GoodEvilFightImpl{public void fight(){System.out.println("北丐洪七公和西毒欧阳锋战斗!");}
}
这两种战斗,前期都要练功,都有相同的准备工作,交给代理对象来做,代理对象在哪?代理对象怎么完成?
public class FightCallback implements MethodInterceptor{public Object intercept(Object object,Method method,Object[] args,MethodProxy proxy) throws Throwable{//前期练功System.out.println("战斗双方正在练功,请不要打扰我们!!!");return proxy.invokeSuper(object,args);}
}
观众又来了,打架在哪里啊
public class Client{public static void main(String[] args){Enhancer enhancer = new Enhancer();enhancer.setSuperclass(QiangQinFightImpl.class);enhancer.setCallback(new RequestCtrlCallback());QiangQinFightImpl fight = (QiangQinFightImpl)enhancer.create();fight.fight();}
}
看到这,好像更傻了。。。嘿嘿嘿。
从代理设计模式到Spring AOP相关推荐
- 从代理机制到Spring AOP
这篇文章准备从Java的代理机制讲到Spring的AOP. 1.代理模式 代理模式是很常见的一种设计模式,代理一词拆开来看就是代为受理,那显然是要涉及到请求被代理的委托方,提供代理的代理方,以及想要通 ...
- 从代理机制到Spring AOP,这篇给你安排的明明白白的
这篇文章准备从Java的代理机制讲到Spring的AOP. 1.代理模式 代理模式是很常见的一种设计模式,代理一词拆开来看就是代为受理,那显然是要涉及到请求被代理的委托方,提供代理的代理方,以及想要通 ...
- 【Spring AOP】静态代理设计模式、Spring 动态代理开发详解、切入点详解(切入点表达式、切入点函数)
AOP 编程 静态代理设计模式 1. 为什么需要代理设计模式 2. 代理设计模式 名词解释 代理开发的核心要素 静态代理编码 静态代理存在的问题 Spring 动态代理开发 搭建开发环境 Spring ...
- 一文带你搞懂从动态代理实现到Spring AOP
摘要:本文主要讲了Spring Aop动态代理实现的两种方式. 1. Spring AOP Spring是一个轻型容器,Spring整个系列的最最核心的概念当属IoC.AOP.可见AOP是Spring ...
- Spring AOP 与代理详解
SpringBoot 系列教程 - 源码地址:https://github.com/laolunsi/spring-boot-examples 大家知道我现在还是一个 CRUD 崽,平时用 AOP 也 ...
- Spring AOP 源码分析 - 创建代理对象
1.简介 在上一篇文章中,我分析了 Spring 是如何为目标 bean 筛选合适的通知器的.现在通知器选好了,接下来就要通过代理的方式将通知器(Advisor)所持有的通知(Advice)织入到 b ...
- 4种实例 advice aop_JAVA动态代理 和 Spring AOP 4种通知的简单实现
学习Spring AOP 之前,先要了解下JAVA的动态代理.如果不清楚动态代理的概念就百度一下吧.废话不多说,直接上代码. 我们模拟一个简单的登录 首先我们创建一个用户登录的接口 package c ...
- Spring Boot实践——Spring AOP实现之动态代理
Spring AOP 介绍 AOP的介绍可以查看 Spring Boot实践--AOP实现 与AspectJ的静态代理不同,Spring AOP使用的动态代理,所谓的动态代理就是说AOP框架不会去修改 ...
- AOP、ASPECT、Spring AOP、JDK动态代理、CGLib动态代理
AOP.ASPECT.Spring AOP.JDK动态代理.CGLib动态代理 1 AOP介绍 1.1 基本定义 AOP(Aspect Oriented Programming)称为面向切面编程,它是 ...
最新文章
- python实例化是什么意思_类实例化和python中的’self’
- 记-php的设计模式
- 蚂蚁算法求解tsp问题matlab,蚁群算法解决TSP问题的MATLAB程序
- Java 10新特性解密
- linux 下小技巧之-统计文件夹下面子文件夹下面的个数
- Linux内核分析-孟宁
- Atitit ati teck trend技术趋势资料包 C:\onedriver\OneDrive\Documents\0 it impttech topic\ati teck trend技术趋
- layedit 内容变化事件_React反应表单与事件
- 网络编程 udp学习笔记补充(帅帅老师讲堂)
- git中将多次commit合并为一次commit
- 2019上半年教资综合素质——主观题
- IPv6网络流量分析及性能监控
- Permission denied (publickey).../RPC failed; curl 92 HTTP/2 stream 0 was.../pack exceeds maximum all
- Elasticsearch:从搜索中获取选定的字段 fields
- 在服务器上下载安装anaconda
- 荒野乱斗1月14日维护服务器,荒野乱斗服务器转移方法介绍_荒野乱斗外服怎么转国服[图文]-游戏窝...
- 30万人追更,年度重磅Go图书出版,百万流量博主带你学习Go底层原理
- @ select 函数使用说明
- 监控系统体系1-数据流监控系统
- (23)Linux基础-系统磁盘阵列raid
热门文章
- 第九课 Java基础篇——面向对象(综合案例)
- python中ret是什么意思_Python ret
- 解决vscode下载速度太慢的问题
- 匈牙利命名和驼峰命名相互转换java
- 关于C++中的一些特殊函数inline,virtual等等
- 物体重心的特点是什么_重心是什么的交点?
- maple 解代数方程组得多项式_Maple笔记2--常微分方程求解
- 网络表示学习Network Representation Learning/Embedding
- ARM汇编:MRS和MSR指令
- Tomcat 解决“At least one JAR was scanned for TLDs yet contained no TLDs”问题