一,简介
代理模式(Proxy),为其他对象提供一种代理以控制对这个对象的访问。与装饰器模式的区别:装饰器模式为了增强功能,而代理模式是为了加以控制
二,角色
Subject
定义了RealSubject和Proxy的共用接口,这样就在任何使用RealSubject的地方都可以使用Proxy
RealSubject
定义Proxy所代表的的真实实体
Proxy
保存一个引用使得代理可以访问实体,并提供一个与Subject的接口相同的接口,这样代理就可以用来替代实体
三,举例
假设有一位小A(RealSubject),想追求小红,但他比较羞涩,所以委托代理小B(Proxy)来处理这件事。
1,类图
2,代码
//定义共用接口(Subject)
class PersuitPeople {
public:
PersuitPeople(string _name):m_sName(_name){}
virtual void persuite() = 0;
string getName() { return m_sName; }
private:
string m_sName;
};
//定义一个真实实体(RealSubject)
class RealPersuitA :public PersuitPeople {
public:
RealPersuitA(string _name) :PersuitPeople(_name) {}
virtual void persuite() {
printf("I love you %s \r\n",this->getName().c_str());
}
};
//代理类 Proxy
class PersuitProxy :public PersuitPeople {
public:
PersuitProxy(string _name):PersuitPeople(_name){}
virtual void persuite() {
m_pRealPersuitA = new RealPersuitA(this->getName());
m_pRealPersuitA->persuite();
}
private:
RealPersuitA* m_pRealPersuitA=nullptr;
};
int main()
{
PersuitProxy *pProxy = new PersuitProxy("小芳");
pProxy->persuite();
system("pause");
return 0;
}
四,优缺点
优点:
1、职责清晰。
2、高扩展性。
3、智能化。
缺点:
1、由于在客户端和真实主题之间增加了代理对象,因此有些类型的代理模式可能会造成请求的处理速度变慢。
2、实现代理模式需要额外的工作,有些代理模式的实现非常复杂。
五,使用场景
在直接访问对象时带来的问题,比如说:要访问的对象在远程的机器上。在面向对象系统中,有些对象由于某些原因(比如对象创建开销很大,或者某些操作需要安全控制,或者需要进程外的访问),直接访问会给使用者或者系统结构带来很多麻烦,我们可以在访问此对象时加上一个对此对象的访问层。
如:
1、Windows 里面的快捷方式。
2、猪八戒去找高翠兰结果是孙悟空变的,可以这样理解:把高翠兰的外貌抽象出来,高翠兰本人和孙悟空都实现了这个接口,猪八戒访问高翠兰的时候看不出来这个是孙悟空,所以说孙悟空是高翠兰代理类。
3、买火车票不一定在火车站买,也可以去代售点。
4、一张支票或银行存单是账户中资金的代理。支票在市场交易中用来代替现金,并提供对签发人账号上资金的控制。
按职责来划分,通常有以下使用场景:
1、远程代理。
2、虚拟代理。
3、Copy-on-Write 代理。
4、保护(Protect or Access)代理。
5、Cache代理。
6、防火墙(Firewall)代理。
7、同步化(Synchronization)代理。
8、智能引用(Smart Reference)代理。
参考:https://blog.csdn.net/peterz1997/article/details/81597768