设计模式学习之装饰模式和代理模式

来源:互联网 发布:top域名不需要备案 编辑:程序博客网 时间:2024/04/27 14:09
学习设计模式的过程应该是一个迭代的过程,学东西的时候不用追求一遍就掌握、理解透彻(很多情况也是不可能的)。看书看不懂、思想没有理解,可以反复去读、去思考。因为实战经验少,书中给出的例子也有限,所以设计模式的学习可以先大概按书中的例子理解,至于真正应用,可以在后面实践中尝试将这些思维融合到考虑过程中。先将这些模式大概了解一下,因为现在实战有限,所以很多模式只能表层体会,后面有时间再回过头来再重新学习,可能会有更深层次的体会


1.装饰模式
定义:动态地给一个对象添加一些额外的职责(不重要的功能,只是偶然一次要执行), 就增加功能来说,装饰模式比生成子类更为灵活。建造过程不稳定,按正确的顺序串联起来进行控制。

描述:当你向旧的类中添加新代码时,一般是为了添加核心职责或主要行为。而当需要加入的仅仅是一些特定情况下才会执行的特定的功能时(简单点就是不是核心应用的功能),就会增加类的复杂度。装饰模式就是把要添加的附加功能分别放在单独的类中,并让这个类包含它要装饰的对象,当需要执行时,客户端就可以有选择地、按顺序地使用装饰功能包装对象。装饰模式是用来包装对象的,每个装饰对象的实现就和如何使用这个对象分离开了,每个装饰对象只关心自己的功能,不需要关心如何被添加到对象链当中,装饰模式是为已有功能动态添加更多功能的一种方式。

实例:

#include <string>#include <iostream>using namespace std;//人class Person{private:string m_strName;public:Person(string strName){m_strName=strName;}Person(){}virtual void Show(){cout<<"装扮的是:"<<m_strName<<endl;}};//装饰类class Finery :public Person{protected:Person* m_component;public:void Decorate(Person* component){m_component=component;}virtual void Show(){m_component->Show();}};//T 恤class TShirts: public Finery{public:virtual void Show(){cout<<"T Shirts"<<endl;m_component->Show();}};//裤子class BigTrouser :public Finery{public:virtual void Show(){cout<<"Big Trouser"<<endl;m_component->Show();}};//客户端int main(){Person *p=new Person("小李");BigTrouser *bt=new BigTrouser();TShirts *ts=new TShirts();bt->Decorate(p);ts->Decorate(bt);ts->Show();return 0;}

 

应用场合:当系统是向旧的类中添加新的代码来实现新功能时,这些新加的代码仅仅是为了满足一些只在某种特定情况下才会执行的特殊行为的需要,装饰模式把每个要装饰的功能放在单独的类中,并让这个类包装它所要装饰的对象,因此,当需要执行特殊行为时,客户代码就可以在运行时根据需要有选择地、按顺序地使用装饰功能包装对象

优点:把类中的装饰功能从类中搬移去除,简化原有的类,有效地把类的核心职责和装饰功能区分开了,而且可以去除相关类中重复的装饰逻辑

2.代理模式
定义:为其他对象提供一种代理以控制对这个对象的访问

描述:代理模式其实就是在访问对象时引入一定程度的间接性,通过这种间接性,附加多种用途,代理就是真实对象的代表。

实例:

#include <string>#include <iostream>using namespace std;//定义接口class Interface{public:virtual void Request()=0;};//真实类class RealClass : public Interface{public:virtual void Request(){cout<<"真实的请求"<<endl;}};//代理类class ProxyClass : public Interface{private:RealClass* m_realClass;public:virtual void Request(){m_realClass= new RealClass();m_realClass->Request();delete m_realClass;}};//客户端:int main(){ProxyClass* test=new ProxyClass();test->Request();return 0;}

应用场合:
远程代理:可以隐藏一个对象在不同地址空间的事实
虚拟代理:通过代理来存放需要很长时间实例化的对象
安全代理:用来控制真实对象的访问权限
智能引用:当调用真实对象时,代理处理另外一些事

原创粉丝点击