Java中的动态代理--JDK动态代理
来源:互联网 发布:如何卸载管家婆软件 编辑:程序博客网 时间:2024/05/22 00:32
首先,我们用一个通俗的例子来理解一下代理。假设有一位明星,他会唱歌和跳舞。那么在这位明星成名之前,我们可以直接找这位明星唱歌和跳舞。但是他出名之后,肯定会找一个经济人,我们再想听这位明星唱歌或者看他跳舞,就只能先找到他的经济人,经纪人可能会向我们收费,然后再安排这位明星唱歌或者跳舞。这个经济人扮演的角色,其实就和我们今天要讲的代理特别相似。代理的目的是拦截对真实业务对象的直接访问。
下面,我们将使用Java代码来实现动态代理。
(1)首先创建一个人类的接口
package com.sunyb.proxy;/** * 人类的接口 */public interface Person { /** * 唱歌方法 * @param songName 歌名 */ public abstract void sing(String songName); /** * 跳舞方法 * @param name 舞蹈名称 * @return */ public abstract String dance(String name);}
(2)然后创建一个明星类,并实现人类接口
package com.sunyb.proxy;/** * 明星类 * @author sunyb * @since 2016-05-21 * @version 1.0 */public class PopStar implements Person { @Override public void sing(String songName) { System.out.println("PopStar is singing " + songName); } @Override public String dance(String name) { System.out.println("PopStar is dancing " + name); return "谢谢你们!"; }}
(3)创建代理对象类
package com.sunyb.proxy;import java.lang.reflect.InvocationHandler;import java.lang.reflect.Method;import java.lang.reflect.Proxy;/** * 明星类的代理类 * @author sunyb * @since 2016-05-21 * @version 1.0 */public class PopStarProxy { public static Object createProxy(final Object targetObject){ /** * @param loader the class loader to define the proxy class * @param interfaces the list of interfaces for the proxy class * to implement * @param h the invocation handler to dispatch method invocations to * @return a proxy instance with the specified invocation handler of a * proxy class that is defined by the specified class loader * and that implements the specified interfaces */ return Proxy.newProxyInstance(targetObject.getClass().getClassLoader(), targetObject.getClass().getInterfaces(), new InvocationHandler() { /** * @param proxy the proxy instance that the method was invoked on * @param method 被调用的方法 * @param args 被调用方法上的参数 * @return * @throws Throwable */ @Override public Object invoke(Object proxy, Method method, Object[] args) throws Throwable { Object result = null; System.out.println("我是代理对象,方法调用前..."); String methodName = method.getName(); switch (methodName){ case "sing": System.out.println("唱歌前,需要先付8000元..."); break; case "dance": System.out.println("跳舞前,需要先付12000元..."); break; default: System.out.println("对不起,该明星没有这项技能!"); break; } //开始调用真实对象的方法 /** * 通过反射的方式调用method方法 * targetObject 是被反射的对象,也就是调用它的method方法 * args是调用该方法时需要的参数 */ result = method.invoke(targetObject, args); System.out.println("我是代理对象,方法调用后..."); return result; } }); }}
(4)编写测试程序
----->唱歌
PopStar popStar = new PopStar(); Person person = (Person) PopStarProxy.createProxy(popStar); person.sing("南山南");
---结果
我是代理对象,方法调用前...
唱歌前,需要先付8000元...
PopStar is singing 南山南
我是代理对象,方法调用后...
--->跳舞
PopStar popStar = new PopStar(); Person person = (Person) PopStarProxy.createProxy(popStar); String result = person.dance("天鹅湖"); System.out.println(result);
--结果
我是代理对象,方法调用前...
跳舞前,需要先付12000元...
PopStar is dancing 天鹅湖
我是代理对象,方法调用后...
谢谢你们!
(5)当业务逻辑复杂时可以像上面这么写,但是当业务简单时,不需要单独创建一个代理类,可以直接这么写:
final PopStar popStar = new PopStar(); Person person = (Person) Proxy.newProxyInstance(popStar.getClass().getClassLoader(), popStar.getClass().getInterfaces(), new InvocationHandler() { @Override public Object invoke(Object proxy, Method method, Object[] args) throws Throwable { System.out.println("唱歌或者跳舞前,需要先给8000块!"); return method.invoke(popStar, args); } }); String result = person.dance("钢管舞"); System.out.println(result);
0 0
- Java中的动态代理--JDK动态代理
- Java JDK中的静态代理、动态代理&Cglib动态代理
- Java JDK中的静态代理、动态代理&Cglib动态代理
- JDK中的动态代理
- JDK中的动态代理
- JDK中的动态代理
- JDK中的动态代理
- jdk中的动态代理
- JDK中的动态代理
- JDK中的动态代理
- JDK中的动态代理
- Java动态代理--jdk代理
- 动态代理--java jdk
- java jdk动态代理
- Java JDK动态代理
- java jdk 动态代理
- Java JDK 动态代理
- java jdk动态代理
- 深度解析Qt中动态链接库
- python利用pyinstaller 生成exe程序(转载)
- CentOS常用的文件操作命令总结
- [分享]mac如何把本地Android项目提交到github
- 2016/5/21请教晓恩
- Java中的动态代理--JDK动态代理
- 189. Rotate Array
- 我一定要学习吗?
- 打印出所有的水仙花数
- CSS float浮动的深入研究、详解及拓展(二)
- Unix系统编程(1) - 文件IO
- BaiduMap提示 java.lang.UnsatisfiedLinkError: Native method not found:
- 表格中有复选框的情形
- Android JSON解析库Gson和Fast-json的使用对比和图书列表小案例