一头扎进设计模式-代理模式
来源:互联网 发布:java统计字母,数字, 编辑:程序博客网 时间:2024/04/29 09:45
定义:为其他对象提供一种代理以控制对这个对象的访问。在某些情况下,一个对象不适合或者不能直接引用另一个对象,而代理对象可以在客户端和目标对象之间起到中介的作用。
用自己的话说:把真正运行的类封装到代理类里面,当实际调用时通过代理类去调用,代理类与真正运行的类实现同一套接口,代理类可以在真正操纵前对动作进行一些处理,适用为
远程代理:远程链接时,通过代理类隐藏网络获取等相关动作。
虚拟代理:使用代理代表开销大的对象或需要安全控制的对象
缓存代理:使用代理判断当前获取的内容是否已被缓存,是则调用缓存返回,否则调用真实的类进行获取。
保护代理:隐藏主体的某些动作,或屏蔽某些数据
java有提供相关api
简单的代理代码:
定义一个主体接口:
public interface Subject { void request();}
定义一个真正的实体类:
public class RealSubject implements Subject { /* (非 Javadoc) * @see com.jjt.proxy.Subject#request() */ @Override public void request() { System.out.println("真正做事的对象执行请求"); }}
定义一个代理:
public class Proxy implements Subject { Subject realSubject = new RealSubject(); /* (非 Javadoc) * @see com.jjt.proxy.Subject#request() */ @Override public void request() { System.out.println("代理类调用实体类"); System.out.println("省略网络请求"); realSubject.request(); }}
测试:
public static void main(String[] args){ Subject proxy = new Proxy();//新建一个代理去请求 proxy.request(); }
结果:
代理类调用实体类省略网络请求真正做事的对象执行请求
———————————————————————————————
动态代理,使用java api
代码:
定义一个人的接口:
/** * 代理与真正执行服务类继承的同个接口 * @author jiangjintai * */public interface PersonBean { String getName(); String getGender(); String getInterests(); int getHotOrNotRating(); void setName(String name); void setGender(String gender); void setInterests(String interests); void setHotOrNotRating(int rating);}
定义一个人的实现:
public class PersonBeanImpl implements PersonBean { String name; String gender; String interests; int rating; int ratingCount = 0 ; public String getName() { return name; } public void setName(String name) { this.name = name; } public String getGender() { return gender; } public void setGender(String gender) { this.gender = gender; } public String getInterests() { return interests; } public void setInterests(String interests) { this.interests = interests; } public int getRating() { return rating; } public void setRating(int rating) { this.rating = rating; } public int getRatingCount() { return ratingCount; } public void setRatingCount(int ratingCount) { this.ratingCount = ratingCount; } /* (非 Javadoc) * @see com.jjt.proxy.javaapi.PersonBean#getHotOrNotRating() */ @Override public int getHotOrNotRating() { // if(ratingCount==0) return 0; return (rating/ratingCount);//返回平均分 } /* (非 Javadoc) * @see com.jjt.proxy.javaapi.PersonBean#setHotOrNotRating(int) */ @Override public void setHotOrNotRating(int rating) {//设置分数 this.rating+=rating; ratingCount++; }}
定义一个handle 用于控制动态代理类对实体类的操作
第一个handle 是不允许用户本人对自己设置分数
/** * InvocationHandler 是代理实例的调用处理程序 实现的接口 * 每个代理实例都具有一个关联的调用处理程序。对代理实例调用方法时,将对方法调用进行编码并将其指派到它的调用处理程序的 invoke 方法 * @author jiangjintai * */public class OwnerInvocationHandler implements InvocationHandler { PersonBean personBean; /** * */ public OwnerInvocationHandler(PersonBean personBean) { this.personBean=personBean; } /* (非 Javadoc) * @see java.lang.reflect.InvocationHandler#invoke(java.lang.Object, java.lang.reflect.Method, java.lang.Object[]) */ @Override public Object invoke(Object proxy, Method method, Object[] args) throws Throwable { if(method.getName().startsWith("get")){ return method.invoke(personBean, args); }else if(method.getName().equals("setHotOrNotRating")){//在这里屏蔽设置分数方法 throw new IllegalAccessError(); }else if(method.getName().startsWith("set")){ return method.invoke(personBean, args); } return null;//别的方法不做处理 }}
第二个handle 是不允许别人对某个用户设置兴趣
public class NonOwnerlnvocationHandler implements InvocationHandler { PersonBean personBean; /** * */ public NonOwnerlnvocationHandler(PersonBean personBean) { this.personBean=personBean; } /* (非 Javadoc) * @see java.lang.reflect.InvocationHandler#invoke(java.lang.Object, java.lang.reflect.Method, java.lang.Object[]) */ @Override public Object invoke(Object proxy, Method method, Object[] args) throws Throwable { if(method.getName().startsWith("get")){ return method.invoke(personBean, args); }else if(method.getName().startsWith("setInterests")){//屏蔽方法 throw new IllegalAccessError(); }else if(method.getName().startsWith("set")){ return method.invoke(personBean, args); } return null; }}
测试方法:
public static void main(String[] args){ PersonBean personBean = new PersonBeanImpl(); personBean.setGender("男"); personBean.setHotOrNotRating(100); personBean.setInterests("下棋"); personBean.setName("泰"); PersonBean ownerProxy = (PersonBean) Proxy.newProxyInstance(personBean.getClass().getClassLoader(), personBean.getClass().getInterfaces(),new OwnerInvocationHandler(personBean)); ownerProxy.setGender("女"); PersonBean nonOwnerProxy = (PersonBean)Proxy.newProxyInstance(personBean.getClass().getClassLoader(),personBean.getClass().getInterfaces(), new NonOwnerlnvocationHandler(personBean)); System.out.println(nonOwnerProxy.getGender()); }
测试:
public static void main(String[] args){ PersonBean personBean = new PersonBeanImpl(); personBean.setGender("男"); personBean.setHotOrNotRating(100); personBean.setInterests("下棋"); personBean.setName("泰"); PersonBean ownerProxy = (PersonBean) Proxy.newProxyInstance(personBean.getClass().getClassLoader(), personBean.getClass().getInterfaces(),new OwnerInvocationHandler(personBean)); ownerProxy.setGender("女");// ownerProxy.setHotOrNotRating(10); 调用该方法抛出java.lang.IllegalAccessError异常 PersonBean nonOwnerProxy = (PersonBean)Proxy.newProxyInstance(personBean.getClass().getClassLoader(),personBean.getClass().getInterfaces(), new NonOwnerlnvocationHandler(personBean)); System.out.println(nonOwnerProxy.getGender());// nonOwnerProxy.setInterests("吹牛");调用该方法抛出java.lang.IllegalAccessError异常 }
0 0
- 一头扎进设计模式-代理模式
- 一头扎进设计模式-适配器模式
- 一头扎进设计模式-组合模式
- 一头扎进设计模式-外观模式
- 一头扎进设计模式-模版模式
- 一头扎进设计模式-命令模式
- 一头扎进设计模式-迭代器模式
- 一头扎进设计模式-观察者模式
- 一头扎进设计模式-状态模式
- 一头扎进设计模式-策略模式
- 一头扎进设计模式-抽象工厂模式
- 一头扎进设计模式-单例模式
- 一头扎进设计模式-装饰者模式
- 设计模式--【代理模式】
- 设计模式:代理模式
- 设计模式--代理模式
- 设计模式---代理模式
- 设计模式-代理模式
- MFC中 怎么将CString转换为string
- MATLAB利用极坐标转换画相对角度相对长度的线段
- 面试/笔试_相似概念比较
- Thinkphp使用PHPMailer发送邮件
- vim多窗口使用技巧
- 一头扎进设计模式-代理模式
- BeanUtils下的各个方法的作用
- Android_AlarmManage及定时发送短信
- ZooKeeper 安装
- 五,Java集合类(3)——List接口及其实现类
- 57. Insert Interval
- 第一本十二章加减乘除
- web magic 爬取京东 一个爬虫实现
- Swift初学【一】