23种设计模式-装饰器(Decorator)设计模式

文章目录

类图: 装饰器设计模式类图

一.什么是装饰器设计模式?

装饰器模式 (Decorator Pattern) 是一种结构型设计模式。它允许在运行时动态地为对象添加新的功能,而无需修改其代码。装饰器模式通过将对象嵌套在装饰器对象中,实现了功能的动态扩展,同时遵循了开放-关闭原则。

二.装饰器模式的特点

  • 运行时动态扩展:通过嵌套装饰器对象,可以动态地为对象增加功能。
  • 与继承的区别:装饰器通过组合来扩展对象功能,而不是通过继承,避免了类爆炸问题。
  • 灵活性:可以使用多个装饰器类,按照需要灵活组合功能。

三.装饰器模式的结构

  • Component(组件接口):定义一个对象接口,可以动态地为其增加职责。
  • ConcreteComponent(具体组件):实现基础功能的类。
  • Decorator(抽象装饰器):实现 Component 接口,并包含一个指向 Component 对象的引用。
  • ConcreteDecorator(具体装饰器) :实现额外的功能,并调用组件对象的原有功能。

四.装饰器模式的优缺点

  • 优点:
    • 动态扩展:可以动态地为对象添加功能。
    • 遵循开放-关闭原则:无需修改原有类的代码即可扩展功能。
    • 灵活性:装饰器可以灵活组合,扩展方式更具弹性。
  • 缺点:
    • 复杂性增加:使用多个装饰器会导致类数量增多,结构变得复杂。
    • 调试困难:由于功能是动态组合的,调试时可能难以定位问题来源。

五.装饰器模式的 C++ 实现

cpp 复制代码
#include <iostream>
#include <memory>
using namespace std;

// 抽象组件
class Component {
public:
    virtual void Operation() const = 0;
    virtual ~Component() = default;
};

// 具体组件
class ConcreteComponent : public Component {
public:
    void Operation() const override {
        cout << "ConcreteComponent: Performing operation." << endl;
    }
};

// 抽象装饰器
class Decorator : public Component {
protected:
    shared_ptr<Component> component; // 持有组件的引用
public:
    Decorator(shared_ptr<Component> comp) : component(move(comp)) {}
    void Operation() const override {
        if (component) {
            component->Operation();
        }
    }
};

// 具体装饰器A
class ConcreteDecoratorA : public Decorator {
public:
    ConcreteDecoratorA(shared_ptr<Component> comp) : Decorator(move(comp)) {}
    void Operation() const override {
        Decorator::Operation(); // 调用原始组件的功能
        AddedBehavior();        // 添加新行为
    }
private:
    void AddedBehavior() const {
        cout << "ConcreteDecoratorA: Adding behavior A." << endl;
    }
};

// 具体装饰器B
class ConcreteDecoratorB : public Decorator {
public:
    ConcreteDecoratorB(shared_ptr<Component> comp) : Decorator(move(comp)) {}
    void Operation() const override {
        Decorator::Operation(); // 调用原始组件的功能
        AddedBehavior();        // 添加新行为
    }
private:
    void AddedBehavior() const {
        cout << "ConcreteDecoratorB: Adding behavior B." << endl;
    }
};

// 客户端代码
int main() {
    shared_ptr<Component> simple = make_shared<ConcreteComponent>();
    cout << "Client: Using a simple component:" << endl;
    simple->Operation();

    shared_ptr<Component> decoratorA = make_shared<ConcreteDecoratorA>(simple);
    cout << "\nClient: Using a component decorated with A:" << endl;
    decoratorA->Operation();

    shared_ptr<Component> decoratorB = make_shared<ConcreteDecoratorB>(decoratorA);
    cout << "\nClient: Using a component decorated with A and B:" << endl;
    decoratorB->Operation();

    return 0;
}

六.装饰器模式的 Java 实现

java 复制代码
// 抽象组件
interface Component {
    void operation();
}

// 具体组件
class ConcreteComponent implements Component {
    @Override
    public void operation() {
        System.out.println("ConcreteComponent: Performing operation.");
    }
}

// 抽象装饰器
abstract class Decorator implements Component {
    protected Component component;

    public Decorator(Component component) {
        this.component = component;
    }

    @Override
    public void operation() {
        if (component != null) {
            component.operation();
        }
    }
}

// 具体装饰器A
class ConcreteDecoratorA extends Decorator {
    public ConcreteDecoratorA(Component component) {
        super(component);
    }

    @Override
    public void operation() {
        super.operation(); // 调用原始组件的功能
        addedBehavior();
    }

    private void addedBehavior() {
        System.out.println("ConcreteDecoratorA: Adding behavior A.");
    }
}

// 具体装饰器B
class ConcreteDecoratorB extends Decorator {
    public ConcreteDecoratorB(Component component) {
        super(component);
    }

    @Override
    public void operation() {
        super.operation(); // 调用原始组件的功能
        addedBehavior();
    }

    private void addedBehavior() {
        System.out.println("ConcreteDecoratorB: Adding behavior B.");
    }
}

// 客户端代码
public class DecoratorPatternExample {
    public static void main(String[] args) {
        Component simple = new ConcreteComponent();
        System.out.println("Client: Using a simple component:");
        simple.operation();

        Component decoratorA = new ConcreteDecoratorA(simple);
        System.out.println("\nClient: Using a component decorated with A:");
        decoratorA.operation();

        Component decoratorB = new ConcreteDecoratorB(decoratorA);
        System.out.println("\nClient: Using a component decorated with A and B:");
        decoratorB.operation();
    }
}

七.代码解析

  • 抽象组件(Component)
    • 提供统一接口 Operation,供所有具体组件和装饰器实现。
    • 使得客户端代码可以以相同的方式使用组件和装饰器。
  • 具体组件(ConcreteComponent)
    • 实现基础功能,例如打印操作信息。
  • 抽象装饰器(Decorator)
    • 持有一个 Component 类型的指针,代表被装饰的对象。
    • 定义通用的装饰行为,默认直接调用被装饰对象的 Operation 方法。
  • 具体装饰器(ConcreteDecoratorA/B)
    • 通过扩展 Decorator 类,增加特定功能。
    • AddedBehavior 方法实现装饰器的额外行为,例如打印装饰信息。
  • 使用 shared_ptr
    • 动态管理对象内存,避免手动管理导致的内存泄漏。

八.总结

装饰器模式提供了一种灵活的方式来动态扩展对象的功能,避免了继承导致的类膨胀问题。通过引入抽象装饰器和具体装饰器,装饰器模式实现了功能的动态组合,使得代码更易于维护和扩展。
应用场景:

  • 动态扩展对象功能:需要在不修改对象代码的情况下,为对象添加功能。
  • 替代子类扩展:避免因为子类扩展功能导致的类爆炸问题。
  • 灵活组合功能:需要根据不同的条件动态组合对象的功能。
相关推荐
ZHOUPUYU2 分钟前
最新SQL Server 2022保姆级安装教程【附安装包】
java·数据库·python·sql·sqlserver·php·sqlserver2022
越努力^越幸运15 分钟前
类和对象--中--运算符重载、日期类实现(重要)
开发语言·c++·算法
IsToRestart18 分钟前
String的设计,用到了哪些设计模式?
java·jvm·设计模式
自律的阿龙29 分钟前
C++练级计划->《多态》虚函数表,菱形继承多态
开发语言·c++
XiaoLeisj31 分钟前
【JavaEE初阶 — 网络编程】TCP流套接字编程
java·开发语言·网络·网络协议·java-ee
MaxCosmos200131 分钟前
读《Effective Java》笔记 - 条目11
java·开发语言·笔记·effective java
yours_Gabriel34 分钟前
【微服务】Nacos配置管理
java·后端·微服务·架构
江-小北1 小时前
Java基础面试题06:hashCode()和equals()方法的重要性体现在什么地方?
java·开发语言
托尼吴1 小时前
第1章-JVM和Java体系架构
java·jvm·架构
大熊的瓜地1 小时前
Android NDK开发 JNI 基础
android·java·ndk