Beverage.h

 #ifndef BEVERAGE_H_INCLUDED
#define BEVERAGE_H_INCLUDED #include <string> class Beverage
{
public:
Beverage( std::string description = "Unknown Beverage" ) : m_description ( description ) {}
virtual std::string getDescription() { return m_description; }
virtual double cost() = ;
private:
std::string m_description;
}; #endif // BEVERAGE_H_INCLUDED

CondimentDecorator.h

 #ifndef CONDIMENTDECORATOR_H_INCLUDED
#define CONDIMENTDECORATOR_H_INCLUDED #include <string>
#include "Beverage.h" class CondimentDecorator : public Beverage
{
public:
virtual std::string getDescription() = ;
}; #endif // CONDIMENTDECORATOR_H_INCLUDED

HouseBlend.h

 #ifndef HOUSEBLEND_H_INCLUDED
#define HOUSEBLEND_H_INCLUDED #include "Beverage.h" class HouseBlend : public Beverage
{
public:
HouseBlend () : Beverage( "House Blend Coffee" ) {}
double cost() { return .; }
}; #endif // HOUSEBLEND_H_INCLUDED

Mocha.h

 #ifndef MOCHA_H_INCLUDED
#define MOCHA_H_INCLUDED #include "CondimentDecorator.h" class Mocha : public CondimentDecorator
{
public:
Mocha ( Beverage * p_beverage ) : m_p_beverage ( p_beverage ) {}
std::string getDescription() { return m_p_beverage->getDescription() + ", Mocha"; }
double cost() { return . + m_p_beverage->cost(); }
private:
Beverage *m_p_beverage;
}; #endif // MOCHA_H_INCLUDED

main.cpp

 #include <iostream>
#include "HouseBlend.h"
#include "Mocha.h"
int main()
{
HouseBlend house_blend;
std::cout << house_blend.getDescription() << ": " << house_blend.cost() << std::endl; Mocha mocha_house_blend( &house_blend );
std::cout << mocha_house_blend.getDescription() << ": " << mocha_house_blend.cost() << std::endl; Mocha mocha_mocha_house_blend( &mocha_house_blend );
std::cout << mocha_mocha_house_blend.getDescription() << ": " << mocha_mocha_house_blend.cost() << std::endl; return ;
}

一点个人理解:

起初对于为什么Mocha类要从CondimentDecorator类继承也就是CondimentDecorator类存在的意义感到疑惑,并做了一次尝试:跳过CondimentDecorator类,让Mocha类直接从Beverage类继承,发现效果是一样的。那为什么还要有CondimentDecorator类的存在呢?

原书上有这么一段解释:

“所有的调料装饰着都必须重新实现getDescription()方法。稍后我们会解释为什么......”

"我们希望叙述不只是描述饮料,而是完整的连调料都描述出来......"

我推测作者的意思是说通过CondimentDecorator类,并且把getDescription方法设置为纯虚函数就可以强制让所有调料类实现此方法。如果不通过getDescription类,那么调料类就可以不实现此方法从而不符合需求。

Headfirst设计模式的C++实现——装饰者模式(Decorater)的更多相关文章

  1. headfirst设计模式(3)—装饰者模式

    序 好久没写设计模式了,自从写了两篇之后,就放弃治疗了,主要还是工作太忙了啊(借口,都是借口),过完年以后一直填坑,填了好几个月,总算是稳定下来了,可以打打酱油了. 为什么又重新开始写设计模式呢?学习 ...

  2. HeadFirst设计模式读书笔记(3)-装饰者模式(Decorator Pattern)

    装饰者模式:动态地将责任附件到对象上.若要扩展功能,装饰者提东了比继承更有弹性的替代方案. 装饰者和被装饰对象有相同的超类型 你可以用一个或者多个装饰者包装一个对象. 既然装饰者和被装饰对象有相同的超 ...

  3. 设计模式(八)装饰器模式Decorator(结构型)

    设计模式(八)装饰器模式Decorator(结构型) 1. 概述 若你从事过面向对象开发,实现给一个类或对象增加行为,使用继承机制,这是所有面向对象语言的一个基本特性.如果已经存在的一个类缺少某些方法 ...

  4. php设计模式课程---7、装饰器模式如何使用

    php设计模式课程---7.装饰器模式如何使用 一.总结 一句话总结: 装饰器的核心是获取了文章类整个类,而不是获取了文章内容,有了这个文章类,我想给你加多少装饰就给你加多少装饰(将文章这个类封装进去 ...

  5. 大型Java进阶专题(八)设计模式之适配器模式、装饰者模式和观察者模式

    前言 ​ 今天开始我们专题的第八课了.本章节将介绍:三个设计模式,适配器模式.装饰者模式和观察者模式.通过学习适配器模式,可以优雅的解决代码功能的兼容问题.另外有重构需求的人群一定需要掌握装饰者模式. ...

  6. 【设计模式 - 9】之装饰者模式(Decorator)

    1      模式简介 装饰者模式允许向一个现有的对象添加新的功能,同时又不改变其结构. 装饰者模式的思路是用"调料"对象将原始对象进行层层包裹,同时其属性.动作层层传递,达到最终 ...

  7. C#设计模式(11)——装饰者模式

    1.装饰者模式介绍 装饰者顾名思义就是对一个类添加一些额外的装饰(功能).我们想给一个对象添加一些额外的功能又不改变对象内方法的签名怎么做呢?最常用的方法就是继承了,子类继承父类,然后重写父类的方法. ...

  8. 《大话设计模式》c++实现 装饰者模式

    一.UML图   介绍 装饰器模式(Decorator Pattern)允许向一个现有的对象添加新的功能,同时又不改变其结构.这种类型的设计模式属于结构型模式,它是作为现有的类的一个包装. 这种模式创 ...

  9. 设计模式(九)装饰者模式(Decorator Pattern)

    一.引言 在软件开发中,我们经常想要对一类对象添加不同的功能,例如要给手机添加贴膜,手机挂件,手机外壳等,如果此时利用继承来实现的话,就需要定义无数的类,如StickerPhone(贴膜是手机类).A ...

随机推荐

  1. 中局域网LAN中建立局域网可访问的类GitHub的服务器

    There are several ways to do this Host internal repositories like Gitlab (free software) or Stash. T ...

  2. freemaker分页备忘

    思路:定义一个freemaker宏,接收参数.然后在freemaker页面上import这个文件,把参数传进来在server端渲染. 分页标签:pager.ftl <#-- 自定义的分页指令. ...

  3. Oracle ABP(Autotask Background Process)

    ABP相当于自动任务与调度程序之间的中介,其主要作用是将自动任务转换成Autotask作业,供调度程序执行.同样重要的是,ABP还维护所有任务执行的历史记录.ABP将其专用资料档案库存储在sysaux ...

  4. 8-14-Exercise

    8-14-小练 这次是我这组出题......我出的是B.C.D[虽然本来是想出的很难......╮(╯▽╰)╭但是,没找到AC1000+同时又让我想出的难题......SO...我出的真的不难= =] ...

  5. Android UI--自定义ListView(实现下拉刷新+加载更多)

    Android UI--自定义ListView(实现下拉刷新+加载更多) 关于实现ListView下拉刷新和加载更多的实现,我想网上一搜就一堆.不过我就没发现比较实用的,要不就是实现起来太复杂,要不就 ...

  6. python学习之元组

    #coding:utf-8# __author__ = 'Administrator'#元组:不可变序列 #空元组mm=()print mm#只有一个值的元组mm=(1,)print mmx=1,2, ...

  7. linux jmail乱码

    在Windows 里面,标题和内容都正常, 在linux里面,--- 1.字符串 more /etc/sysconfig/i18n   export LANG=en_US.UTF-8 ====默认是e ...

  8. div:给div加滚动栏 div的滚动栏设置

    今天做了个样例: div 的滚动栏问题: 两种方法: 一. <div style=" overflow:scroll; width:400px; height:400px;”>& ...

  9. CardsTube/YouTubePlaylist

    CardsTube https://github.com/DesarrolloAntonio/CardsTube YouTubePlaylist https://github.com/akoscz/Y ...

  10. CenOS搭建FTP服务器

    CenOS搭建FTP服务器 -------------------------------------------------------------------------准备工作--------- ...