浅谈装饰者模式

作者: 肖某 | 来源:发表于2020-01-03 00:35 被阅读0次

0、先上需求

需求V1.0:聚会上,男的喝酒,女的喝饮料,用代码实现。
聪明的你,肯定说这个简单。UML类图一画,代码立马跟上。

image.png
/**
 * @author xiaoqqq by 2020/1/2 22:49
 * @desc: 人
 */
public abstract class Person {

    /**
     * 具体喝啥,子类自己去实现
     */
    public abstract void drink();
}
/**
 * @author xiaoqqq by 2020/1/2 22:51
 * @desc: 男性
 */
public class Male extends Person {

    @Override
    public void drink() {
        System.out.println("喝酒");
    }
}

/**
 * @author xiaoqqq by 2020/1/2 22:51
 * @desc: 女性
 */
public class Females extends Person {

    @Override
    public void drink() {
        System.out.println("喝饮料");
    }
}

完工,你以为你写完了,实际上也只是你觉得写完了。

需求V2.0,所有会唱歌的男同胞,喝酒之前唱首歌,不会唱歌的男同胞,喝酒之前说个笑话。
聪明的你,心想简单!马上安排……

需求V2.0 UML类图
image.png

代码就不给了,从上面的UML类图就可以看出,你设计的思路是采用面向对象的继承。这种方法当然是可以的,但是存在几个问题:

  • 如果父类是final的,不允许你继承怎么办?
  • 需求一直迭代,某天你的子类越来越多,父类的某个方法需要被改的时候,你所有子类怎么办?

其实有一种设计模式,它的名字叫“装饰者模式”,它能帮你解决以上两个问题。接着往下看~

1、定义

动态的给一个对象添加一些额外的职责,就增加功能来说,装饰者模式比生成子类更为灵活。也可以说,装饰者模式是一种继承关系的替代。

2、UML类图

image.png

3、代码实现

Step1: 定一个抽象的组件类

/**
 * @author xiaoqqq by 2020/1/2 22:49
 * @desc: 人
 */
public abstract class Person {

    /**
     * 具体喝啥,子类自己去实现
     */
    public abstract void drink();
}

Step2: 定义一个抽象的装饰者类

/**
 * @author xiaoqqq by 2020/1/3 00:10
 * @desc: 抽象的装饰者类
 */
public abstract class Decorator extends Person {

    private Person person;

    public Decorator(Person male) {
        this.person = male;
    }

    @Override
    public void drink() {
        person.drink();
    }
}

Step3: 定一个具体的被装饰者类(组件类的具体实现类)

/**
 * @author xiaoqqq by 2020/1/3 00:11
 * @desc: 装饰者的具体实现类,实现喝酒之前先唱歌
 */
public class CanSingMale extends Decorator {

    public CanSingMale(Person person) {
        super(person);
    }

    @Override
    public void drink() {
        sing();
        super.drink();
    }

    private void sing() {
        System.out.println("唱歌");
    }

}

Step4: 客户端调用

/**
 * @author xiaoqqq by 2020/1/2 22:52
 * @desc: 程序入口
 */
public class TestMain {

    public static void main(String[] args) {
        Person male = new Male();
        Decorator decorator = new CanSingMale(male);
        decorator.drink();
    }
}

4、总结

4.1、优点
  • 继承方案的替代,避免类爆炸。
  • 就增强功能而言,比类继承更为灵活,可扩展性更高。
4.2、缺点
  • 多层装饰逻辑复杂

相关文章

  • 再谈装饰者模式(总结)

    在之前的文章 浅谈装饰者模式+JAVA I/O中的装饰者模式 中,浅谈了一下装饰者模式,这篇文章来总结一下装饰者模...

  • 浅谈装饰者模式

    0、先上需求 需求V1.0:聚会上,男的喝酒,女的喝饮料,用代码实现。聪明的你,肯定说这个简单。UML类图一画,代...

  • 如何利用装饰者模式在不改变原有对象的基础上扩展功能

    目录 什么是装饰者模式 普通示例 装饰者模式示例 类图关系 装饰者模式使用场景 装饰者模式优点 装饰者模式缺点 什...

  • 装饰者模式

    装饰者模式 装饰者模式和适配器模式对比 装饰者模式 是一种特别的适配器模式 装饰者与被装饰者都要实现同一个接口,主...

  • java IO 的知识总结

    装饰者模式 因为java的IO是基于装饰者模式设计的,所以要了解掌握IO 必须要先清楚什么事装饰者模式(装饰者模式...

  • 浅谈装饰者模式+JAVA I/O中的装饰者模式

    1. 装饰者模式 举个栗子,假如在一家饮料店中有两种饮料,分别是奶茶和咖啡,相对的有三种调料,蜂蜜、块糖和摩卡,这...

  • 设计模式-装饰者模式

    装饰者模式概念: 装饰者模式又名包装(Wrapper)模式。装饰者模式以对客户端透明的方式扩展对象的功能,是继承关...

  • java - 装饰者模式

    装饰者模式 装饰者模式:动态将责任添加到对象上。如果需要扩展功能,装饰者提供了比继承更有弹性的解决方案。装饰者模式...

  • 设计模式之装饰者模式(Decorator Pattern)

    What: 装饰者模式又名包装(Wrapper)模式。装饰者模式动态地将责任附加到对象身上。若要扩展功能,装饰者提...

  • 装饰者(Decorator)模式

    装饰者(Decorator)模式装饰模式又名包装(Wrapper)模式。装饰模式是继承关系的一个替代方案。装饰模式...

网友评论

    本文标题:浅谈装饰者模式

    本文链接:https://www.haomeiwen.com/subject/ewlaoctx.html