装饰器模式(Decorator) C++
装饰器模式是比较常用的一种设计模式,Python中就内置了对于装饰器的支持。
具体来说,装饰器模式是用来给对象增加某些特性或者对被装饰对象进行某些修改。

如上图所示,需要被装饰的对象在最上方,它自身可以有自己的实例,一般通过抽象类来实现(Java中也可以通过接口实现)。
右侧中间是一个装饰器类或者接口,其实内容与原对象基本一致,不过我们自定义的装饰器一般会继承这个装饰器基类。
最下层就是具体的装饰器了,可以看到,具体装饰器类中需要包含被装饰对象成员(也就是说,装饰器需要和被装饰对象有同样的子类),然后增加一些额外的操作。
下面的代码是一个买煎饼的例子,如我们生活中所见,可以选基础煎饼(鸡蛋煎饼,肉煎饼等),然后再额外加别的东西:
#include<iostream>
#include<string>
using namespace std; class Pancake//基类
{
public:
string description = "Basic Pancake";
virtual string getDescription(){ return description; }
virtual double cost() = ;
}; class CondimentDecorator :public Pancake//装饰器基类
{
public:
string getDescrition();
}; class MeatPancake :public Pancake//肉煎饼
{
public:
MeatPancake(){ description = "MeatPancake"; }
double cost(){ return ; }
};
class EggPancake :public Pancake//鸡蛋煎饼
{
public:
EggPancake(){ description = "EggPancake"; }
double cost(){ return ; }
}; class Egg :public CondimentDecorator//额外加鸡蛋
{
public:
Pancake* base;
string getDescription(){ return base->getDescription() + ", Egg"; }
Egg(Pancake* d){ base = d; }
double cost(){ return base->cost() + 1.5; }
};
class Potato :public CondimentDecorator//额外加土豆
{
public:
Pancake* base;
string getDescription(){ return base->getDescription() + ", Potato"; }
Potato(Pancake* d){ base = d; }
double cost(){ return base->cost() + ; }
};
class Bacon :public CondimentDecorator//额外加培根
{
public:
Pancake* base;
string getDescription(){ return base->getDescription() + ", Bacon"; }
Bacon(Pancake* d){ base = d; }
double cost(){ return base->cost() + ; }
}; int main()
{
Pancake* pan = new EggPancake();
pan = &Potato(pan);
pan = &Bacon(pan);
cout << pan->getDescription() << " $ : " << pan->cost() << endl;
system("pause");
return ;
}
可以看到,Pancake是煎饼的基类,这个基类因为定义了纯虚函数cost,所以不能被实例化。同样,装饰器基类CondimentDecorator也不能被实例化。
后面,EggPancake和MeatPancake是Pancake的派生类,是实际存在的类。
Egg、Bacon和Potato就是我们定义的装饰器对象,其中包含了Pancake的指针,可以对Pancake及其派生类进行操作。
运行代码的结果如下:

即我们选择了一个鸡蛋煎饼,然后额外加了土豆和培根,一共5+1+2=8块。
装饰器模式的优点:
1、可以轻松对已存在的对象进行修改和包装,在被装饰者的前面或者后面添加自己的行为,而无需修改原对象。
2、可以动态、不限量地进行装饰,可以更灵活地扩展功能。
相对地,装饰器模式有很明显的缺点:
1、会加入大量的小类,即使只添加一个功能,也要额外创建一个类,使得程序更复杂。
2、增加代码复杂度,使用装饰器模式不但需要实例化组件,还要把组件包装到装饰者中。
装饰器模式(Decorator) C++的更多相关文章
- 【PHP设计模式 09_ZhuangShiQi.php】装饰器模式 (decorator)
<?php /** * [装饰器模式 (decorator)] * 有时候发布一篇文章需要经过很多人手,层层处理 */ header("Content-type: text/html; ...
- 设计模式(八)装饰器模式Decorator(结构型)
设计模式(八)装饰器模式Decorator(结构型) 1. 概述 若你从事过面向对象开发,实现给一个类或对象增加行为,使用继承机制,这是所有面向对象语言的一个基本特性.如果已经存在的一个类缺少某些方法 ...
- 装饰器模式-Decorator(Java实现)
装饰器模式-Decorator(Java实现) 装饰器模式允许向一个现有的对象添加新的功能, 同时又不改变其结构. 其中 "现有对象"在本文中是StringDisplay类. 添加 ...
- 说说设计模式~装饰器模式(Decorator)~多功能消息组件的实现
返回目录 为何要设计多功能消息组件 之前写过一篇装饰器模式的文章,感觉不够深入,这次的例子是实现项目中遇到的,所以把它拿出来,再写写,之前也写过消息组件的文章,主要采用了策略模式实现的,即每个项目可以 ...
- 装饰器模式(Decorator)
转自http://blog.csdn.net/hust_is_lcd/article/details/7884320 1.认识装饰器模式 装饰模式能够实现动态的为对象添加功能,是从一个对象外部来给对象 ...
- 设计模式入门之装饰器模式Decorator
//装饰模式定义:动态地给一个对象加入一些额外的职责. //就添加功能来说.装饰模式比生成子类更为灵活 //这也提现了面向对象设计中的一条基本原则,即:尽量使用对象组合,而不是对象继承 //Compo ...
- 装饰器模式(Decorator)——深入理解与实战应用
本文为原创博文,转载请注明出处,侵权必究! 1.初识装饰器模式 装饰器模式,顾名思义,就是对已经存在的某些类进行装饰,以此来扩展一些功能.其结构图如下: Component为统一接口,也是装饰类和被装 ...
- 装饰器模式 Decorator 结构型 设计模式 (十)
引子 现实世界的装饰器模式 大家应该都吃过手抓饼,本文装饰器模式以手抓饼为模型展开简介 "老板,来一个手抓饼, 加个培根, 加个鸡蛋,多少钱?" 这句话会不 ...
- 设计模式学习心得<装饰器模式 Decorator>
装饰器模式(Decorator Pattern)允许向一个现有的对象添加新的功能,同时又不改变其结构.这种类型的设计模式属于结构型模式,它是作为现有的类的一个包装. 这种模式创建了一个装饰类,用来包装 ...
- 23种设计模式之装饰器模式(Decorator Pattern)
装饰器模式(Decorator Pattern) 允许向一个现有的对象添加新的功能,同时又不改变其结构.这种类型的设计模式属于结构型模式,它是作为现有的类的一个包装. 这种模式创建了一个装饰类,用来包 ...
随机推荐
- SUPEROBJECT序列数据集为JSON
// SUPEROBJECT 序列数据集 cxg 2017-1-12// {"data":[{"c1":1,"c2":1}]};// DEL ...
- 【sourcetree】sourcetree连接远程仓库需要登陆但是一直登陆不上的问题 解决方法
授权类型选用 基础 .只需要登陆你在bitbucket的用户名和密码 如下 .即可成功连接远程仓库
- Go -- 实现二叉搜索树
树: https://suanfa.herokuapp.com/3%E6%A0%91/binarytree/ 数据结构 首先我们定义需要的数据结构.注意,TreeNode的左右节点都是*TreeNod ...
- win7安装ANT
点击进入ant官网,找到下载选项. 选择下载安装文件.其余的源文件和手册的下载步骤完全相同. 可以下载官网上对应系统的最新版本.也可以在old ant 版本中选择自己需要的版本.笔者需要ant ...
- jmeter Plugins Manager插件管理
在 https://jmeter-plugins.org/downloads/all/ 下载插件,放到lib/ext Download plugins-manager.jar and put it i ...
- iOS10你掉坑了吗?
坑1: 系统导航栏上按键消失问题 坑2: canOpenURL 调用返回NO问题 坑3: iOS10 权限崩溃问题 坑4: xib不好用了?别怕看这里! 坑5: command +/注释失效 坑6: ...
- centos 7 卸載 mysql
跟網上文章,安裝了一個mysqlwget http://repo.mysql.com/mysql-community-release-el7-5.noarch.rpm 記下卸載過程: 首先执行查看命令 ...
- RecyclerView的万能切割线
效果图: 用法: 加入默认切割线:高度为2px.颜色为灰色 mRecyclerView.addItemDecoration(new RecycleViewDivider(mContext, Linea ...
- 自动检查出修改的代码 shell 做升级包 供观摩
#!/bin/bash # 检测出 appsReleass 项目代码更新 # oath 冉幕飞 #验证 基础参数 $1 day=$1 #多少天内 zipfile=$2 #包名称 if [ " ...
- 【转载】一致性哈希算法(consistent hashing)
一致性哈希算法在1997年由麻省理工学院提出的一种分布式哈希(DHT)实现算法,设计目标是为了解决因特网中的热点(Hot spot)问题,初衷和CARP十分类似.一致性哈希修正了CARP使用的简 单哈 ...