1. 程式人生 > >裝飾模式(Decorator Pattern)

裝飾模式(Decorator Pattern)

-- trac uml null spl line making app cto

模式定義

裝飾模式(Decorator Pattern)
動態地給一個對象增加一些額外的職責,就增加對象功能來說,裝飾模式比生成子類實現更為靈活。

UML類圖

技術分享圖片

  • 抽象構件(Component) 需要被裝飾的類,定義了對象的接口,裝飾器可以給它增加額外的職責(方法)
  • 具體構建(Concrete Component)實現了接口,裝飾器可以給它增加額外的職責(方法)
  • 抽象裝飾類(Decorator) 抽象構件的子類,並有關聯抽象構件類,方便調用構件方法(確保在原有方法上修改或添加職能)用於給具體構件增加職責,但是具體職責在其子類中實現
  • 具體裝飾類(Concrete Decorator)

    代碼結果

      public static class DecoratorApp
    {
        public static void Run()
        {
            ConcreteComponent c = new ConcreteComponent();
            ConcreteDecoratorA d1 = new ConcreteDecoratorA();
            ConcreteDecoratorB d2 = new ConcreteDecoratorB();
    
            d1.SetComponent(c);
            d2.SetComponent(d1);
    
            d2.Operation();
    
            Console.ReadKey();
        }
    }
    public abstract class Componet
    {
        public abstract void Operation();
    }
    public class ConcreteComponent : Componet
    {
        public override void Operation()
        {
            Console.WriteLine("Concrete Component.Operation()");
        }
    }
    public abstract class Decorator : Componet
    {
        protected Componet component;
    
        public void SetComponent(Componet component)
        {
            this.component = component;
        }
        public override void Operation()
        {
            if (component != null)
            {
                component.Operation();
            }
        }
    }
    public class ConcreteDecoratorA : Decorator
    {
        public override void Operation()
        {
            base.Operation();
            Console.WriteLine("Concrete DecoratorA.Operation()");
        }
    }
    public class ConcreteDecoratorB : Decorator
    {
        public override void Operation()
        {
            base.Operation();
            Console.WriteLine("Concrete DecoratorB.Operation()");
            AddedBehavior();
        }
        void AddedBehavior()
        {
            Console.WriteLine("add behavior");
        }
    }

    情景模式

    這裏以圖書館借閱為例,圖書館可借閱的有書和光盤,將書和光盤抽象為可借閱的東西。通過裝飾類添加借閱功能。

      public static class RealWorldDecoratorApp
    {
        public static void Run()
        {
            Book book = new Book() { Author = "Worley", Title = "Inside ASP.NET", NumCopies = 10 };
            book.Display();
    
            Video video = new Video() { Director = "Spielberg", Title = "Jaws", NumCopies = 23, PlayTime = 92 };
            video.Display();
    
            Console.WriteLine("\nMaking video borrowable:");
    
            Borrowable borrowvideo = new Borrowable(video);
            borrowvideo.BorrowItem("Customer #1");
            borrowvideo.BorrowItem("Customer #2");
    
            borrowvideo.Display();
        }
    }
    public abstract class LibraryItem
    {
        public int NumCopies { get; set; }
        public abstract void Display();
    }
    public class Book : LibraryItem
    {
        public string Author { get; set; }
        public string Title { get; set; }
    
        public override void Display()
        {
            Console.WriteLine("\nBook-----");
            Console.WriteLine("Author:{0}", this.Author);
            Console.WriteLine("Title:{0}", this.Title);
            Console.WriteLine("# Copies:{0}", NumCopies);
        }
    }
    
    public class Video : LibraryItem
    {
        public string Director { get; set; }
        public string Title { get; set; }
    
        public int PlayTime { get; set; }
    
        public override void Display()
        {
            Console.WriteLine("\nVideo-----");
            Console.WriteLine("Director:{0}", this.Director);
            Console.WriteLine("Title:{0}", this.Title);
            Console.WriteLine("# Copies:{0}", NumCopies);
            Console.WriteLine("Playtime:{0}", this.PlayTime);
        }
    }
    public abstract class Decorator : LibraryItem
    {
        protected LibraryItem libraryItem;
        public Decorator(LibraryItem libraryItem)
        {
            this.libraryItem = libraryItem;
        }
        public override void Display()
        {
            libraryItem.Display();
        }
    }
    public class Borrowable : Decorator
    {
        protected List<string> borrowers = new List<string>();
        public Borrowable(LibraryItem libraryItem)
            : base(libraryItem)
        {
        }
        public void BorrowItem(string name)
        {
            borrowers.Add(name);
            libraryItem.NumCopies--;
        }
        public void ReturnItem(string name)
        {
            borrowers.Remove(name);
            libraryItem.NumCopies++;
        }
        public override void Display()
        {
            base.Display();
    
            foreach (string borrower in borrowers)
            {
                Console.WriteLine(" borrower " + borrower);
            }
        }
    }

裝飾模式(Decorator Pattern)