如何理解Java设计模式的装饰模式

技术如何理解Java设计模式的装饰模式这篇文章主要介绍“如何理解Java设计模式的装饰模式”,在日常操作中,相信很多人在如何理解Java设计模式的装饰模式问题上存在疑惑,小编查阅了各式资料,整理出简单好用的操作方法,希望

本文主要介绍“如何理解Java设计模式的装饰器模式”。在日常操作中,相信很多人对于如何理解Java设计模式的装饰器模式问题都有疑问。边肖查阅了各种资料,整理出简单易用的操作方法,希望能帮助大家解答“如何理解Java设计模式的decorator模式”的疑惑!接下来,请和边肖一起学习!

一、前言

装饰器模式实际上提倡的是组合而不是继承的做法。个人认为,要理解decorator模型,首先要理解为什么需要组合而不是继承,为什么继承让人深恶痛绝。

为什么建议用组合代替继承?

面向对象的特性包括继承和封装,但它们之间存在矛盾。继承是指子类依赖于父类中的实现,一旦父类中的实现发生变化,就会影响子类,这是打破封装的一种表现形式,而组合就是巧妙地利用封装来实现继承函数的代码重用。

二、什么是装饰模式

1.定义:

装饰器模式也称为Wrapper模式。装饰器模式以对客户端透明的方式扩展对象的功能,这是继承关系的一种替代。

2.意图

动态地给对象添加一些额外的职责。在添加函数方面,Decorator模式比生成子类更灵活。

00-1010包装

00-1010有时我们想给一个对象而不是整个类添加一些函数。例如,图形用户界面工具箱允许您向任何用户界面模块添加一些组件,如边框,或一些行为,如窗口滚动。

00-1010让类在不修改原始接口的情况下表现得更好。

3.别名

自然,继承也有一些问题。

继承会导致超类和子类之间的强耦合。当超类改变时,子类也会改变。

超类的内部细节对子类是可见的,继承通常被认为会破坏封装。

4.动机

如何理解Java设计模式的装饰模式

在装饰器模式中的角色有:

组件角色:给出一个抽象接口,并标准化准备接受额外职责的对象。

具体组件角色:定义一个将接受额外职责的类。

装饰角色:保存一个组件对象的实例,并定义一个与抽象组件接口一致的接口。

混凝土装饰者角色:负责给组件对象附加额外的职责。

00-1010 1.有必要扩展一个类的功能或者给一个类增加额外的职责。

2.需要向对象动态添加函数,这些函数可以动态撤销。

3.需要增加大量由一些基本函数的排列组合而成的函数。

5.作用

优点:

1.装饰模式和继承的目的是扩展对象的功能,但是装饰模式比继承更灵活。

2.设计师可以通过使用不同的混凝土装饰类以及这些类的排列和组合来创建许多不同行为的组合。

3.装饰器模式具有良好的可扩展性

缺点:

装饰器模式会导致设计中出现许多小对象。如果过度使用,会使程序更加复杂。而且对象多了会很难出错,尤其是长得都差不多的时候。

6.问题

///摘要

///手机抽象类,即decorator模式下的抽象组件类。

////摘要

publicabstractclassPhone

{

publicatabstractvoitprint();

}

///摘要

///苹果手机,也就是装饰图案中的具体组件类。

  /// </summary>
    public class ApplePhone:Phone
    {
        /// <summary>
        /// 重写基类方法
        /// </summary>
        public override void Print()
        {
            Console.WriteLine("开始执行具体的对象——苹果手机");
        }
    }
     /// <summary>
    /// 装饰抽象类,要让装饰完全取代抽象组件,所以必须继承自Photo
    /// </summary>
    public abstract class Decorator:Phone
    {
        private Phone phone;
         public Decorator(Phone p)
        {
            this.phone = p;
        }
         public override void Print()
        {
            if (phone != null)
            {
                phone.Print();
            }
        }
    }
     /// <summary>
    /// 贴膜,即具体装饰者
    /// </summary>
    public class Sticker : Decorator
    {
        public Sticker(Phone p)
            : base(p)
        { 
        }
         public override void Print()
        {
            base.Print();
             // 添加新的行为
            AddSticker();      
        }
         /// <summary>
        /// 新的行为方法
        /// </summary>
        public void AddSticker()
        {
            Console.WriteLine("现在苹果手机有贴膜了");
        }
    }
     /// <summary>
    /// 手机挂件
    /// </summary>
    public class Accessories : Decorator
    {
        public Accessories(Phone p)
            : base(p)
        {
        }
         public override void Print()
        {
            base.Print();
             // 添加新的行为
            AddAccessories();          
        }
         /// <summary>
        /// 新的行为方法
        /// </summary>
        public void AddAccessories()
        {
            Console.WriteLine("现在苹果手机有漂亮的挂件了");
        }
    }

客户端代码

class Customer
    {
        static void Main(string[] args)
        {
            // 我买了个苹果手机
            Phone phone = new ApplePhone();
             // 现在想贴膜了
            Decorator applePhoneWithSticker = new Sticker(phone);
            // 扩展贴膜行为
            applePhoneWithSticker.Print();
            Console.WriteLine("----------------------\n");
             // 现在我想有挂件了
            Decorator applePhoneWithAccessories = new Accessories(phone);
            // 扩展手机挂件行为
            applePhoneWithAccessories.Print();
            Console.WriteLine("----------------------\n");
             // 现在我同时有贴膜和手机挂件了
            Sticker sticker = new Sticker(phone);
            Accessories applePhoneWithAccessoriesAndSticker = new Accessories(sticker);
            applePhoneWithAccessoriesAndSticker.Print();
            Console.ReadLine();
        }

从上面的客户端代码可以看出,客户端可以动态地将手机配件增加到手机上,如果需要添加手机外壳时,此时只需要添加一个继承Decorator的手机外壳类,从而,装饰模式扩展性也非常好。

七、装饰模式的.NET应用

在.NET 类库中也有装饰者模式的实现,该类就是System.IO.Stream

MemoryStream memoryStream = new MemoryStream(new byte[] {95,96,97,98,99});
             // 扩展缓冲的功能
            BufferedStream buffStream = new BufferedStream(memoryStream);
             // 添加加密的功能
            CryptoStream cryptoStream = new CryptoStream(memoryStream,new AesManaged().CreateEncryptor(),CryptoStreamMode.Write);
            // 添加压缩功能
            GZipStream gzipStream = new GZipStream(memoryStream, CompressionMode.Compress, true);

到此,关于“如何理解Java设计模式的装饰模式”的学习就结束了,希望能够解决大家的疑惑。理论与实践的搭配能更好的帮助大家学习,快去试试吧!若想继续学习更多相关知识,请继续关注网站,小编会继续努力为大家带来更多实用的文章!

内容来源网络,如有侵权,联系删除,本文地址:https://www.230890.com/zhan/76876.html

(0)

相关推荐

  • berkeleydb应用(berkeleydb环境是什么)

    技术MySQL不再支持Berkeley DB 转而添加插件的示例分析这篇文章将为大家详细讲解有关MySQL不再支持Berkeley DB 转而添加插件的示例分析,小编觉得挺实用的,因此分享给大家做个参考,希望大家阅读完这

    攻略 2021年12月17日
  • 怎么使用Python功能

    技术怎么使用Python功能这篇文章主要讲解了“怎么使用Python功能”,文中的讲解内容简单清晰,易于学习与理解,下面请大家跟着小编的思路慢慢深入,一起来研究和学习“怎么使用Python功能”吧!变量赋值正如函数*ar

    攻略 2021年10月29日
  • java中的迭代器模式怎么实现

    技术java中的迭代器模式怎么实现小编给大家分享一下java中的迭代器模式怎么实现,相信大部分人都还不怎么了解,因此分享这篇文章给大家参考一下,希望大家阅读完这篇文章后大有收获,下面让我们一起去了解一下吧!迭代器模式迭代

    攻略 2021年11月17日
  • 好听的字男,古代男生好听的名3个字

    技术好听的字男,古代男生好听的名3个字必须是苏姓好听的字男。怎么起都好听。苏小白都好听。苏小明都能扛得住。苏花花都有萌萌的赶脚。万搭。更新:苏大强旋风强势来袭
    but 苏家三个娃的名字都很好听啊
    普普通通的字,苏明玉,

    生活 2021年11月1日
  • Windows下怎么安装Frida环境

    技术Windows下怎么安装Frida环境今天就跟大家聊聊有关 Windows下怎么安装Frida环境,可能很多人都不太了解,为了让大家更加了解,小编给大家总结了以下内容,希望大家根据这篇文章可以有所收获。 Window

    攻略 2021年10月23日
  • Python基础知识-1.7标识符和关键字

    技术Python基础知识-1.7标识符和关键字 Python基础知识-1.7标识符和关键字一、标识符上图看完了,那什么是标识符
    答:在程序中定义的一些符号和名称
    二、作用
    前面学习变量了,下面的代码,此

    礼包 2021年12月5日