C#设计模式学习之装饰者模式

        写这个随笔时,其实对该模式理解的并不是十分透彻。在此想到什么写什么,希望对自己对他人有所帮助。

        装饰者模式主要是应用继承和组合的思想,极大的实现了程序的多态,使得的程序有了更高的扩展性。

 

  第一个基础例子:

      这里假如我们要实现有这么一群人,他们都要穿西服。那么我们首先建立这个人类。

  代码如下:

      

   class Person
    {
        private string name;  //要装扮的人的名称
        public Person()
        {
         
        }
        public Person(string _name) 
        {
            this.name = _name;
        }
        public virtual void Show()   //注意此处是虚方法
        {
            Console.WriteLine("装扮的人是:{0}", this.name);
        }
    }

        然后构建西服类,代码如下

  class Suit:Person
    {
        Person component = null;  //穿西服的人

        public void Decorate(Person _component)  //把要穿西服的人传递到该类(组合思想)
        {
            this.component = _component;
        }
        public override void Show()
        {
             //如果有穿西服的人
            if (component != null)
            {
                component.Show();
            }
            Console.WriteLine("穿上西服");
        }
    }

            假如我们给小明和小红分别穿上西服,Main方法的代码如下

 static void Main(string[] args)
        {
            Person xiaoming = new Person("小明");
            Person xiaohong = new Person("小红");
            Suit suit = new Suit();

            //装扮小明
            suit.Decorate(xiaoming);
            suit.Show();

            //装扮小红
            suit.Decorate(xiaohong);
            suit.Show();

            Console.ReadKey();
        }

      运行结果如下

       

      类图结构如下

 

---------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------

      第二个基础例子:

       假如此时需求变了,我们的不仅要给小明和小红穿西服,我们还要给小狗阿黄穿西服,那该如何修改原程序呢。

       开始扩展代码

      此时我们新建一个Animal的抽象类

  abstract class Animal  //抽象的Animal类
    {
        protected string name;
        public Animal()
        {

        }
        public Animal(string _name)
        {
            this.name = _name;
        }
        public abstract void Show();   //原来Person的虚方法则改为对应的抽象方法
    }

    然后我们继续新建Person类和Dog类,都继承Animal类

 class Person : Animal  //人类,继承自Animal类
    {
        public Person(string _name) : base(_name)
        {

        }
        public override void Show()   //实现Animal类的抽象方法
        {
            Console.WriteLine("装扮的人{0}", base.name);
        }
    }
    class Dog : Animal   //够类,继承自Animal类
    {
        public Dog(string _name) : base(_name)
        {

        }
        public override void Show()  //实现Animal类的抽象方法
        {
            Console.WriteLine("装扮的狗{0}", base.name);
        }
    }

接下来我们分别给小明小红和阿黄穿上西服

 static void Main(string[] args)
        {
            Person xiaoming = new Person("小明");
            Person xiaohong = new Person("小红");
            Dog ahuang = new Dog("阿黄");

             //装扮小明和小红
            Suit suit = new Suit();
            suit.Decorate(xiaoming);
            suit.Show();
            suit.Decorate(xiaohong);
            suit.Show();
            //装扮阿黄
            suit.Decorate(ahuang);
            suit.Show();
 

            Console.ReadKey();
        }

运行结果如下

      

类结构图如下,此时我们可以看到人和狗都继承自Animal,实现了一次的扩展的

--------------------------------------------------------------------------------------------------------------------------------------------------------------------------------

第三个基础例子

       此时我们不仅想让小明小红阿黄穿西服了,我们还想让他们穿鞋子,打领带,并且以后可能会有更多的衣服供他们选择(变成奇迹暖暖了);

       我们在第二个例子的基础上继续修改,满足需求

       此时,我们将原来的Suit类改成抽象的衣服类,然后分别让Suit,Shoes和Sneake类继承自衣服类来实现

      首先构造衣服类,代码如下

    class Finery : Animal   //此处继承Animal的抽象类,从而实现了所有类都继承自Animal类,在Derorate组合获得的component的字段,都可以使用Show()方法,从而达到一层一层装扮的目的
    {

        protected Animal component;   
        public void Decorate(Animal _component)  //注意:此处是组合的思想,主要是为了把要修饰的主体放到该类的component字段中
        {
            this.component = _component;
        }
        public override void Show()
        {
            if (component != null)
            {
                component.Show();
            }
        }
    }

    然后分别构造西服,鞋子,领带类,代码如下

class Sneake : Finery
    {
        public override void Show()//此处实现的最上层Animal的抽象类
        {
            base.Show();
            Console.WriteLine("系上领带");
        }
    }
    class Shoes : Finery
    {
        public override void Show()//此处实现的最上层Animal的抽象类
        {
            base.Show();
            Console.WriteLine("穿上鞋子");
        }
    }
    class Suit : Finery
    {
        public override void Show()//此处实现的最上层Animal的抽象类
        {
            base.Show();
            Console.WriteLine("穿上西服");
        }
    }

        接下来开始给小红小明和阿黄装扮,代码如下

static void Main(string[] args)
        {
            //实例化所有被装饰的主体
            Person xiaoming = new Person("小明");
            Person xiaohong = new Person("小红");
            Dog ahuang = new Dog("阿黄");
             //实例化所有装饰
            Suit suit = new Suit();
            Sneake sneake = new Sneake();
            Shoes shoes = new Shoes();

            suit.Decorate(xiaoming);
            sneake.Decorate(suit);
            shoes.Decorate(sneake);
            shoes.Show();
            Console.WriteLine();
            suit.Decorate(xiaohong);
            sneake.Decorate(suit);
            shoes.Decorate(sneake);
            shoes.Show();
            Console.WriteLine();
            //狗就不系领带了
            shoes.Decorate(ahuang);
            suit.Decorate(shoes);
            suit.Show();

            Console.ReadKey();
        }

运行结果如下:

   

类图结构如下

      

 

总结:

        装饰者模式的难点在于多继承,存在组合的思想,将最高层次的被继承的类(Animal)组合(Decorate)在装饰类(Finery)中,通过base.Show()方法来一层一层的展现(这点有点绕,很像俄罗斯套娃,需要跟一下程序,一开始不太好理解)。

        最后,如果有其他错误,欢迎指出,谢谢

 

posted on 2018-02-06 11:16  鲁广广  阅读(178)  评论(0编辑  收藏  举报

导航