Component 是定义一个对象接口,可以给这些对象动态的添加职责。ConcreteComponent 是定义了一个具体的对象,也可以给这个对象添加一些职责。Decorator装饰抽象类,继承了Component,从外类赖扩展Component类的功能,单对于Component来说,是无需知道Decorator的存在的。 至于ConcreteDecorator就是具体的装饰对象,起到给Component添加职责的功能。
装饰模式是利用SetComponent来对对象进行包装的。每个装饰对象的实现就和如何使用这个对象分离开了,每个装饰对象只关心自己的功能,,不需要关心如何被添加到对象链当中。
如果只有一个ConcreteComponent类而没有抽象的Component类,那么Decorator类可以是ConcreteComponent的一个子类。 同样道理,如果只有一个ConcreteDecorator类,那么久没有必要建立一个单独的Decorator类,二可以把Decorator和ConcreteDecorator的责任合并成一个类。
装饰模式总结:
装饰模式是为已有功能动态地添加更多功能的一种方式。
当系统需要新功能时,是向旧的类中添加新的代码。这些新加的代码通常装饰了原有类的核心职责或主要行为。
在主类中加入了新的字段,新的方法和新的逻辑,从而增加了主类的复杂度。而这些新加入的东西仅仅是为了满足一些旨在某种特定情况下才会执行的特殊行为的需要。而装饰模式却提供了一个非常好的解决方案,它把每个要装饰的功能放在单独的类中,并让这个类包装它所要装饰的对象,因此,当需要执行特殊行为时,客户代码就可以在运行时根据需要有选择的、按顺序地使用装饰功能包装对象了。
装饰模式的装饰顺序很重要,比如加密数据和过滤词汇都可以是数据持久化前的装饰功能,若先加密了数据再用过滤功能就会出问题了。最理想的情况,保证装饰类之间彼此独立,这样就可以以任意的顺序进行组合了。
基本代码:
using System;
using System.Collections.Generic;
using System.Text;
namespace 装饰模式
{
class Program
{
static void Main(string[] args)
{
ConcreteComponent c = new ConcreteComponent();//具体组件
ConcreteDecoratorA d1 = new ConcreteDecoratorA();//具体装饰器A
ConcreteDecoratorB d2 = new ConcreteDecoratorB();//具体装饰器B
d1.SetComponent(c);
d2.SetComponent(d1);
d2.Operation();//具体对象的操作(c) 具体装饰对象A的操作(d1) 具体装饰对象B的操作(d2)
Console.Read();
}
}
//抽象组件
abstract class Component
{
public abstract void Operation();
}
//具体组件
class ConcreteComponent : Component
{
public override void Operation()
{
Console.WriteLine("具体对象的操作");
}
}
//抽象装饰器
abstract class Decorator : Component
{
protected Component component;
public void SetComponent(Component component)//设置组件:传入具体的组件
{
this.component = component;
}
//重写Operation() 实际执行的是Component的Operation
public override void Operation()//调用抽象组件的操作
{
if (component != null)
{
component.Operation();
}
}
}
//具体装饰器A
class ConcreteDecoratorA : Decorator
{
private string addedState;//添加变量
public override void Operation()
{
base.Operation();
addedState = "New State";
Console.WriteLine("具体装饰对象A的操作");
}
}
//具体装饰器B
class ConcreteDecoratorB : Decorator
{
public override void Operation()
{
base.Operation();
AddedBehavior();
Console.WriteLine("具体装饰对象B的操作");
}
private void AddedBehavior()//添加方法
{
}
}
}
具体对象的操作
具体装饰对象A的操作
具体装饰对象B的操作
小菜扮靓:
using System;
using System.Collections.Generic;
using System.Text;
namespace 装饰模式
{
class Program
{
static void Main(string[] args)
{
Person xc = new Person("小菜");
Console.WriteLine("\n第一种装扮:");
Sneakers pqx = new Sneakers();//破球鞋
BigTrouser kk = new BigTrouser();//垮裤
TShirts dtx = new TShirts();//大T恤
pqx.Decorate(xc);
kk.Decorate(pqx);
dtx.Decorate(kk);
dtx.Show();
Console.WriteLine("\n第二种装扮:");
LeatherShoes px = new LeatherShoes();//皮鞋
Tie ld = new Tie();//领带
Suit xz = new Suit();//西装
px.Decorate(xc);
ld.Decorate(px);
xz.Decorate(ld);
xz.Show();
Console.WriteLine("\n第三种装扮:");
Sneakers pqx2 = new Sneakers();//破球鞋
LeatherShoes px2 = new LeatherShoes();//皮鞋
BigTrouser kk2 = new BigTrouser();//垮裤
Tie ld2 = new Tie();
pqx2.Decorate(xc);
px2.Decorate(pqx2);
kk2.Decorate(px2);
ld2.Decorate(kk2);
ld2.Show();
Console.Read();
}
}
//具体组件类
class Person
{
public Person()
{ }
private string name;
public Person(string name)
{
this.name = name;
}
public virtual void Show()
{
Console.WriteLine("装扮的{0}", name);
}
}
//服饰类 ---装饰类
class Finery : Person
{
protected Person component;
//打扮
public void Decorate(Person component)
{
this.component = component;
}
public override void Show()
{
if (component != null)
{
component.Show();
}
}
}
//具体服饰类:大T恤
class TShirts : Finery
{
public override void Show()
{
Console.Write("大T恤 ");
base.Show();
}
}
//具体服饰类:垮裤
class BigTrouser : Finery
{
public override void Show()
{
Console.Write("垮裤 ");
base.Show();
}
}
//具体服饰类:破球鞋
class Sneakers : Finery
{
public override void Show()
{
Console.Write("破球鞋 ");
base.Show();
}
}
//具体服饰类:西装
class Suit : Finery
{
public override void Show()
{
Console.Write("西装 ");
base.Show();
}
}
//具体服饰类:领带
class Tie : Finery
{
public override void Show()
{
Console.Write("领带 ");
base.Show();
}
}
//具体服饰类:皮鞋
class LeatherShoes : Finery
{
public override void Show()
{
Console.Write("皮鞋 ");
base.Show();
}
}
}