1、概念
装饰模式是在不必改变原类文件和使用继承的情况下,动态地扩展一个对象的功能。它是通过创建一个包装对象,也就是装饰来包裹真实的对象.
装饰者模式原则:多用组合,少用继承。
二、装饰者UML图
三、UML分析
Component(标准的装饰模式抽象类),它声明了一些操作,它具体的类讲进行重载以实现自己特定的操作。这个Component具体类是模式中的被装饰者,Component父类可以被细化为另一个叫做Decorator的抽象类,即装饰者抽象类。Decorator类中包含了一个Component的引用。Decorator的具体类为Component或者Decorator定义了几个扩展行为,并且会在自己的操作中内嵌Component操作。
四、装饰模式应用场景
###需求:
首先进行需求分析,星巴克里有种类繁多的咖啡,结账时我们需要知道咖啡的名称和价格。所以,我们很容易想到抽出一个咖啡基类,然后继承实现各个种类的咖啡。但是,这样做的问题是,星巴克里有几十种饮料,如果我们给每种咖啡都创建一个类,会导致类数目过于庞大,而且星巴克也在不断地推出新的品种,这会给我们系统的维护带来不小的麻烦。
接下来我们进一步分析,造成咖啡饮料价格不同的原因在于:
咖啡本身的种类不同(比如,咖啡可以分为浓缩咖啡(Espresso)、无咖啡因咖啡(Decaf)、深度烘焙咖啡(DarkRoast)等)。
咖啡里加的调料(牛奶、豆浆、抹茶、摩卡等)不同。
所以,我们可以将问题简化成:
咖啡饮料的价格 = 咖啡本身的价格 + 各种调料的价格
###分析:
我们看到,Milk 就像一个“装饰者(Decorator)”,而 Espresso 就像一个“被装饰者(Component)”,可以在“被装饰者”上添加各种“装饰者”来制作出全新口味的 Espresso 咖啡,当然也可以把“装饰者”放在其它类别的“被装饰者”上。只要对“被装饰者”和“装饰品”进行组合,我们就能制作出各种各样的咖啡。
需要格外强调的是,这里的组合要求是动态地进行组合,即装饰者与被装饰者是在运行的时候绑定,而不是写死在类里(比如继承,类继承是在编译的时候增加行为,而装饰者模式是在运行时增加行为)。在接下来装饰者模式的实现过程中,很多实现细节都是为了达到这个目标。
五、装饰模式的优缺点
1、把类中的装饰功能从类中搬移出去,这样可以简化原有的类。
2、当有效的把类中的核心功能和装饰功能区分开了,可以去除相关类中重复的装饰逻辑。