装饰模式

层层包装,增强功能。这就是装饰模式的要旨!装饰器模式就是基于对象组合的方式,可以很灵活的给对象添加所需要的功能。它把需要装饰的功能放在单独的类中,并让这个类包装它所要装饰的对象。

意图:

动态的给一个对象添加一些额外的职责。就增加功能来说,Decorator模式相比生成子类模式更为灵活。

适用性:

1、在不影响其它对象的情况下,以动态、透明的方式给单个对象添加职责。

2、处理那些可以撤销的职责。

3、希望为某个对象而不是一整个类添加一些功能时。

4、当不能采用生成子类的方法进行扩充时。一种情况是,可能有大量独立的扩展,为支持每一种组合将产生大量的子类,使得子类数呈爆炸性增长。另一种情况可能是因为类定义被隐藏,或类定义不能用于生成子类。

效果:

1、比静态继承更为灵活。继承机制会产生许多新类,增加了系统的复杂度。而装饰可以使你对一些职责进行混合和匹配。

2、避免在层次结构高层的类有太多的特征。扩展一个复杂类的时候,很可能会暴露出与添加职责无关的细节。你可以定义一个简单的类,并且用装饰逐渐的添加功能。

3、会产生许多小对象。

4、Decorator与Component不一样,Decorator是一个透明的包装。如果我们从对象标识的观点出发,一个被装饰了的组件与这个组件是有差别的,因此,使用装饰时不应该依赖对象标识。

注意:

1、接口的一致性。装饰对象的接口必须与它所装饰的Component的接口是一致的。

2、省略抽象的Docorator类。当你仅需要添加一个职责的时,没有必要定义抽象Decorator类。你常常需要处理显存的类层次结构而不是设计一个新系统,这时你可以把Decorator向Component转发请求的职责合并到ConcreteDecorator中。

3、保持Component类的简单性。为了保证接口的一致性,组件和装饰必须有一个共同的Component父类。因此保持这个类的简单些是很重要的。

参与者:

Component

——定义一个对象接口,可以给这些对象动态的添加职责。

ConcreteComponent

——定义一个对象,可以给这个对象添加一些职责。

Decorator

——维持一个指向Component对象的指针,并定义一个与Component接口一致的接口。

ConcreteDecorator

——向组件添加职责。

UML:

代码实现:在控制台打印如下表格,基本的姓名、年龄、学历、性别必须拥有,其它如英语等级等属性自由添加。

打印一行表格代码:

void print(char* str)
{
cout<<"├───────────────────────────────"<<endl
<<"│"<<str<<":"<<endl;
}

定义一个抽象基类absTable(Component)

class absTable
{
public:
virtual void putTable() = ;
};

定义具体的表格absTable(ConcreteComponent)

class BaseTable:public absTable
{
public:
virtual void putTable()
{
print("姓名");
print("性别");
print("学历");
print("年龄");
cout<<"└───────────────────────────────"<<endl;
}
};

定义抽象Decorator

class Decorator:public absTable
{
public:
Decorator(absTable* concrateTb):mpAbsTable(concrateTb){} virtual void putTable()
{
mpAbsTable->putTable();
}
private:
absTable* mpAbsTable;
};

定义具体的装饰EnglishDcrt、CurWage、Experience(ConcreteDecoratorA、B、C)

class EnglishDcrt:public Decorator
{
public:
EnglishDcrt(absTable* pTb):Decorator(pTb){} virtual void putTable()
{
print("英语等级");
Decorator::putTable();
}
};
class CurWage:public Decorator
{
public:
CurWage(absTable* pTb):Decorator(pTb){} virtual void putTable()
{
print("当前薪水");
Decorator::putTable();
}
};
class Experience:public Decorator
{
public:
Experience(absTable* pTb):Decorator(pTb){} virtual void putTable()
{
print("项目经验");
Decorator::putTable();
}
};

客户端代码:

#include <iostream>
#include "Decorator.h" using namespace std; //动态的给一个对象添加一些额外的职责!
//层层包装,增强功能。这就是装饰模式的要旨!
//接口稳定不变! void main()
{
BaseTable pro1;
cout<<"初始表格:"<<endl<<endl;
pro1.putTable(); cout<<"新表格1:"<<endl<<endl;
EnglishDcrt eng(&pro1);
eng.putTable(); cout<<"新表格2:"<<endl<<endl;
CurWage wg(&eng);
wg.putTable(); cout<<"新表格3:"<<endl<<endl;
Experience ex(&wg);
ex.putTable();
}

部分结果:

这样我们实现了项目经验、当前薪水、英语等级的自由组合,当然还可以添加更多的属性。

装饰模式(Decorator)C++实现的更多相关文章

  1. 装饰模式/decorator模式/结构型模式

    装饰模式Decorator 定义 为对象动态的增加新的功能,实现要求装饰对象和被装饰对象实现同一接口或抽象类,装饰对象持有被装饰对象的实例. java实现要点 定义一个接口或抽象类,作为被装饰者的抽象 ...

  2. 二十四种设计模式:装饰模式(Decorator Pattern)

    装饰模式(Decorator Pattern) 介绍动态地给一个对象添加一些额外的职责.就扩展功能而言,它比生成子类方式更为灵活.示例有一个Message实体类,某个对象对它的操作有Insert()和 ...

  3. 乐在其中设计模式(C#) - 装饰模式(Decorator Pattern)

    原文:乐在其中设计模式(C#) - 装饰模式(Decorator Pattern) [索引页][源码下载] 乐在其中设计模式(C#) - 装饰模式(Decorator Pattern) 作者:weba ...

  4. 设计模式 装饰模式(Decorator)

    设计模式 装饰模式(Decorator) @author ixenos 装饰模式是什么 1.装饰模式以对客户端透明的方式对象的功能,是继承关系的一个替代方案,但装饰模式可以在不创造更多子类的情况下,对 ...

  5. 设计模式-装饰模式(Decorator Pattern)

    装饰模式(Decorator Pattern):动态地给一个对象添加一些额外的职责,就增加功能来说,装饰模式比生成子类更为灵活

  6. Netty学习-IO体系架构系统回顾 & 装饰模式Decorator的具体使用

    Netty学习-IO体系架构系统回顾 IO和NIO的学习 NIO - 1.4 开始出的 在网络应用框架中,NIO得到了大量的使用,特别是netty里面 前提:对IO及其了解 对IO的总结和回顾 理解J ...

  7. 设计模式-09装饰模式(Decorator Pattern)

    1.模式动机 一般有两种方式可以实现给一个类或对象增加行为: 继承机制:使用继承机制是给现有类添加功能的一种有效途径,通过继承一个现有类可以使得子类在拥有自身方法的同时还拥有父类的方法.但是这种方法是 ...

  8. 设计模式系列之装饰模式(Decorator Pattern)——扩展系统功能

    说明:设计模式系列文章是读刘伟所著<设计模式的艺术之道(软件开发人员内功修炼之道)>一书的阅读笔记.个人感觉这本书讲的不错,有兴趣推荐读一读.详细内容也可以看看此书作者的博客https:/ ...

  9. 装饰模式 - Decorator 和 外观模式 - Facade

    装饰模式 Decorator,不改变接口但动态给对象加入责任,所需功能按顺序串联起来控制,比生成子类灵活. 外观模式 Facade,让接口更简单.为子系统中的一组接口提供一个一致的界面. 参考:

  10. [工作中的设计模式]装饰模式decorator

    一.模式解析 装饰模式又名包装(Wrapper)模式.装饰模式以对客户端透明的方式扩展对象的功能,是继承关系的一个替代方案. 装饰模式的要点主要是: 1.需要对已有对象扩展新的功能,又不希望改变原有对 ...

随机推荐

  1. 程序员客栈与DaoCloud这两家企业联手后,运维工程师要失业了!

    2017年1月11日 ,程序员客栈与DaoCloud正式建立合作伙伴关系,为创业企业和团队提供容器应用解决方案.通过与DaoCloud合作,客栈可以更有效地把控开发环节中的不确定因素,解决项目工期不确 ...

  2. node jsonwebtoken

     jsonwebtoken是node版本的JWT(JSON Web Tokens)的实现.1.什么是JWT?Json web token (JWT), 是为了在网络应用环境间传递声明而执行的一种基于J ...

  3. JAVA中浅复制与深复制

    1.浅复制与深复制概念⑴浅复制(浅克隆)被复制对象的所有变量都含有与原来的对象相同的值,而所有的对其他对象的引用仍然指向原来的对象.换言之,浅复制仅仅复制所考虑的对象,而不复制它所引用的对象. ⑵深复 ...

  4. 【Android】进程间通信IPC——AIDL

    AIDL官网定义AIDL(Android 接口定义语言)与您可能使用过的其他 IDL 类似. 您可以利用它定义客户端与服务使用进程间通信 (IPC) 进行相互通信时都认可的编程接口. 在 Androi ...

  5. 记录:Ubuntu下升级Python从2.x到3.x

    一.安装Python3 在Ubuntu中的终端输入:sudo apt-get install python3 提示资源被锁住,可能有另外一个程序在占用此资源. 解决方法:输入以下指令解锁资源 sudo ...

  6. 分别用for循环,while do-while以及递归方法实现n的阶乘!

    分别用for循环,while do-while以及递归方法实现n的阶乘! 源码: package book;import java.util.Scanner;public class Access { ...

  7. SSO 单点登录解决方案

    转自:http://www.blogjava.net/Jack2007/archive/2014/03/11/191795.html 1 什么是单点登陆      单点登录(Single Sign O ...

  8. Python学习笔记之模块与包

    一.模块 1.模块的概念 模块这一概念很大程度上是为了解决代码的可重用性而出现的,其实这一概念并没有多复杂,简单来说不过是一个后缀为 .py 的 Python 文件而已 例如,我在某个工作中经常需要打 ...

  9. 9.在idea中创建Maven项目

    1.新建maven WEB项目 打开-File-New-Project 点击NEXT 2.选择项目组,并给项目命名 3.选择maven路径 添加的配置为 archetypeCatalog=intern ...

  10. 学习EXTJS6(3)基本概念

    ExtJS不再纠缠HTML和CSS上.概念和传统的程序相近.如面板panel,布局Layout.组件Component等等. 1.渲染Render:ExtJS页面在浏览器中装载完成后完全展现出来的一个 ...