1. 意图
动态地给一个对象添加一些额外的职责。就增加功能来说, D e c o r a t o r模式相比生成子类更为灵活。
2. 动机
有时我们希望给某个对象而不是整个类添加一些功能。例如,一个图形用户界面工具箱允许你对任意一个用户界面组件添加一些特性,例如边框,或是一些行为,例如窗口滚动。使用继承机制是添加功能的一种有效途径,从其他类继承过来的边框特性可以被多个子类的实例所使用。但这种方法不够灵活,因为边框的选择是静态的,用户不能控制对组件加 边框的方式和时机。
动态地给一个对象添加一些额外的职责。就增加功能来说, D e c o r a t o r模式相比生成子类更为灵活。
2. 动机
有时我们希望给某个对象而不是整个类添加一些功能。例如,一个图形用户界面工具箱允许你对任意一个用户界面组件添加一些特性,例如边框,或是一些行为,例如窗口滚动。使用继承机制是添加功能的一种有效途径,从其他类继承过来的边框特性可以被多个子类的实例所使用。但这种方法不够灵活,因为边框的选择是静态的,用户不能控制对组件加 边框的方式和时机。
3.举例
C++代码:
#ifndef DECORATOR_H
#define DECORATOR_H
#include <iostream>
#include <string>
using std::string;
using std::cout;
using std::endl;
class CMeal{
private:
string m_strName;
public:
CMeal(){}
CMeal(string temp): m_strName(temp){}
virtual void GetName(){
cout<<m_strName<<" ";
}
};
class CNoodle : public CMeal{
public:
CNoodle(): CMeal("noodle"){}
};
class CDumpling : public CMeal{
public:
CDumpling() : CMeal("dumpling"){}
};
class CDressing : public CMeal{
private:
CMeal* meal;
public:
CDressing(CMeal* temp){meal = temp;}
virtual void GetName(){
meal->GetName();
}
};
class CVinegar : public CDressing{
public:
CVinegar(CMeal* temp): CDressing(temp){}
virtual void GetName(){
CDressing::GetName();
cout<<"with vinegar"<<" ";
}
};
class COil : public CDressing{
public:
COil(CMeal* temp): CDressing(temp){}
virtual void GetName(){
CDressing::GetName();
cout<<"with oil"<<" ";
}
};
#endif
#include <iostream>
#include "decorator.h"
int main(){
CMeal* firstMeal=new CVinegar(new COil(new CNoodle));
firstMeal->GetName();
cout<<endl;
CMeal* secondMeal=new CVinegar(new CDumpling);
secondMeal->GetName();
cout<<endl;
return 0;
}