Android设计模式之代理模式 Proxy

一.概述
代理模式也是平时比较常用的设计模式之一,代理模式其实就是提供了一个新的对象,实现了对真实对象的操作,或成为真实对象的替身.在日常生活中也是很常见的.例如A要租房,为了省麻烦A会去找中介,中介会替代A去筛选房子,A坐享中介筛选的结果,并且交房租也是交给中介,这就是一个典型的日常生活中代理模式的应用.平时打开网页,最先开到的一般都是文字,而图片等一些大的资源都会延迟加载,这里也是使用了代理模式.
代理模式的组成:
:抽象主题-声明真实主题和代理主题共同的接口
Real :真实主题-真实的对象,需要被代理主题引用
Proxy :代理主题-因为引用了,并且实现了跟一样的接口,所以可以操作,还可以提供一些附加操作,例如 & after
代理模式常用基于场景的分类:
1. Proxy:虚拟代理其实就是通过代理的模式对消耗资源比较大的对象做了一个延迟加载,就是什么时候用到这个对象才去创建它.
2. Proxy:远程代理是比较经典的应用了,类似于C/S模式(主要拦截并控制远程方法的调用,做代理防火墙之类的).
3.SmartProxy:智能引用代理可以给引用的对象提供一些额外的操作,例如实现里面中介和 的动作.
4. Proxy;保护代理可以控制一个对象的访问,必要时候提供一系列的权限管理.
5.Copy-on-write Proxy:写时拷贝(克隆)代理其实是 Proxy的分支,提供了拷贝大对象的时候只有在对象真正变化后才会进行拷贝(克隆)的操作(延迟拷贝).
代理模式的优缺点:
优点:
1.代理作为调用着和真实对象的中间层,降低了模块间和系统的耦合性
2.可以以一个小对象代理一个大对象,达到优化系统提高运行速度的目的
3.提供的权限管理
4.容易扩展,和都接口化了,更改业务后只要接口不变,可以不做任何修改.
缺点:
1.同优点1,因为调用者和真实对象多了一个中间层,所以会增加调用响应的时间
二.实现
这里就拿A找中介租房为Demo来构建代理模式.
1.普通代理
根据场景先定义一个抽象主题,,提供三个方法,分别是获取房屋信息,签合同和付租金.
/*** Created by jesse on 15-7-24.*/public interface IHouse {void getHouseInfo();void signContract();void payFees();}
接下来定义真实主题,并实现接口.增加房屋名称和价格两个属性,填充借口方法,在获取房屋信息的时候就把房屋名称和价格log出来;签合同的时候log出签合同的时间,付租金的时候log出价格.
public class House implements IHouse{private final String TAG = House.class.getSimpleName();private String name;private double price;public House(String name, double price){this.name = name;this.price = price;}@Overridepublic void getHouseInfo() {Log.i(TAG, "House Info- name:" + name + "¥:" + price);}@Overridepublic void signContract() {Log.i(TAG, "Contract:" + name + "signed at" +new SimpleDateFormat("HH:mm:ss").format(SystemClock.uptimeMillis()));}@Overridepublic void payFees() {Log.i(TAG, "Bill: name-" + name + "$-" + price);}}
定义房屋代理,同样需要实现接口,并持有House的引用.可以看到代理类其实就像有封装House,提供了一些附加操作,例如客户要看房子的时候代理会先检索自己库存的房屋信息,签合同之前要准备合同之类的.
public class ProxyHouse implements IHouse{private final String TAG = ProxyHouse.class.getSimpleName();private IHouse house;public ProxyHouse(IHouse house){this.house = house;}@Overridepublic void getHouseInfo() {Log.i(TAG, "searching");house.getHouseInfo();Log.i(TAG, "search finished");}@Overridepublic void signContract() {Log.i(TAG, "prepare contract");house.signContract();}@Overridepublic void payFees() {house.payFees();}}