设计模式:桥接模式

桥接模式

  • [1. 定义](#1. 定义)
  • [2. 画笔问题](#2. 画笔问题)
  • [3. 主要优点](#3. 主要优点)
  • [4. 主要缺点](#4. 主要缺点)
  • [5. 应用场景](#5. 应用场景)

1. 定义

桥接模式(Bridge Pattern):旨在将抽象部分和实现部分解耦,使它们可以独立地变化。这种模式通过将抽象和实现分离,使它们可以独立地进行扩展和修改,而不会相互影响。它是一种对象结构型模式,又称为柄体(Handle and Body)模式或接口(Interface)模式。

2. 画笔问题

假如需要使用大、中、小3种型号的画笔来绘制红、黑、蓝3种不同的颜色。如果我们使用工厂模式,就需要支持9种规格的笔的制造,而且如果红色改色度了,那红大、红中、红小都需要一起改。所以我们使用桥接模式,将颜色与大小分离开,颜色与大小的扩展与修改就不会影响到对方。

cpp 复制代码
#include <iostream>

// 颜色接口
class Color {
public:
    virtual void applyColor() = 0;
};

// 黑色
class BlackColor : public Color {
public:
    void applyColor() override {
        std::cout << "Applying black color." << std::endl;
    }
};

// 红色
class RedColor : public Color {
public:
    void applyColor() override {
        std::cout << "Applying red color." << std::endl;
    }
};

// 蓝色
class BlueColor : public Color {
public:
    void applyColor() override {
        std::cout << "Applying blue color." << std::endl;
    }
};

// 画笔抽象类
class Brush {
protected:
    Color* color;

public:
    Brush(Color* color) : color(color) {}

    virtual void draw() = 0;
};

// 大画笔
class LargeBrush : public Brush {
public:
    LargeBrush(Color* color) : Brush(color) {}

    void draw() override {
        std::cout << "Using large brush. ";
        color->applyColor();
    }
};

// 中画笔
class MediumBrush : public Brush {
public:
    MediumBrush(Color* color) : Brush(color) {}

    void draw() override {
        std::cout << "Using medium brush. ";
        color->applyColor();
    }
};

// 小画笔
class SmallBrush : public Brush {
public:
    SmallBrush(Color* color) : Brush(color) {}

    void draw() override {
        std::cout << "Using small brush. ";
        color->applyColor();
    }
};

int main() {
    // 创建不同型号和颜色的画笔
    Color* blackColor = new BlackColor();
    Color* redColor = new RedColor();
    Color* blueColor = new BlueColor();

    Brush* largeBrush = new LargeBrush(blackColor);
    Brush* mediumBrush = new MediumBrush(redColor);
    Brush* smallBrush = new SmallBrush(blueColor);

    // 使用不同型号和颜色的画笔进行绘画
    largeBrush->draw();
    mediumBrush->draw();
    smallBrush->draw();

    // 释放内存
    delete blackColor;
    delete redColor;
    delete blueColor;
    delete largeBrush;
    delete mediumBrush;
    delete smallBrush;

    return 0;
}

我们定义了Color接口和具体的颜色类BlackColor、RedColor和BlueColor,用于表示不同的颜色。然后,我们定义了Brush抽象类和具体的画笔类LargeBrush、MediumBrush和SmallBrush,用于表示不同的画笔型号。在画笔类中,通过组合颜色类来实现画笔和颜色的桥接。

在main函数中,我们创建了不同型号和颜色的画笔对象,并使用它们进行绘画操作。通过桥接模式,我们可以方便地扩展画笔和颜色的种类,而且它们之间的变化是相互独立的,改变一方不会影响到另一方。

但是看到这个实现,用东北话说有一种咋看咋不得劲的感觉,就是颜色是分离出去了,但是大小这属性还是和笔紧紧绞在一起。我们尝试将颜色与大小都分离出来,进一步增加灵活性。

cpp 复制代码
#include <iostream>

// 笔的颜色的虚基类
class Color {
public:
    virtual std::string getColor() const = 0;
};

// 具体的笔的颜色类
class BlackColor : public Color {
public:
    std::string getColor() const override {
        return "Black";
    }
};

class RedColor : public Color {
public:
    std::string getColor() const override {
        return "Red";
    }
};

class BlueColor : public Color {
public:
    std::string getColor() const override {
        return "Blue";
    }
};

// 笔的大小的虚基类
class Size {
public:
    virtual std::string getSize() const = 0;
};

// 具体的笔的大小类
class SmallSize : public Size {
public:
    std::string getSize() const override {
        return "Small";
    }
};

class MediumSize : public Size {
public:
    std::string getSize() const override {
        return "Medium";
    }
};

class LargeSize : public Size {
public:
    std::string getSize() const override {
        return "Large";
    }
};

// 笔类
class Brush {
private:
    const Size* size;
    const Color* color;

public:
    Brush(const Size* s, const Color* c)
        : size(s), color(c) {}

    void draw() const {
        std::cout << "Using " << size->getSize() << " brush to draw with " << color->getColor() << " color" << std::endl;
    }
};

int main() {
    const Size* smallSize = new SmallSize();
    const Size* mediumSize = new MediumSize();
    const Size* largeSize = new LargeSize();

    const Color* blackColor = new BlackColor();
    const Color* redColor = new RedColor();
    const Color* blueColor = new BlueColor();

    Brush smallBlackBrush(smallSize, blackColor);
    Brush mediumRedBrush(mediumSize, redColor);
    Brush largeBlueBrush(largeSize, blueColor);

    smallBlackBrush.draw();
    mediumRedBrush.draw();
    largeBlueBrush.draw();

    delete smallSize;
    delete mediumSize;
    delete largeSize;
    delete blackColor;
    delete redColor;
    delete blueColor;

    return 0;
}

这个代码看着一下子舒服很多,这也是桥接模式,Brush类作为抽象部分的扩展,将具体的颜色和大小对象组合在一起。

3. 主要优点

(1)分离抽象和实现:桥接模式通过将抽象部分和实现部分分离,使它们可以独立变化。这样可以更灵活地扩展和修改系统的功能,而不会影响到其他部分的代码。

(2)扩展性强:由于抽象部分和实现部分解耦,可以很方便地扩展新的抽象部分和实现部分,而且它们之间可以自由组合,避免了类爆炸问题。

(3)避免多重继承:在很多情况下,桥接模式可以取代多层继承方案。多层继承方案违背了单一职责原则,复用性较差,且类的个数非常多。桥接模式是比多层继承方案更好的解决方法,它极大地减少了子类的个数。

(4)可维护性高:桥接模式将系统划分为多个维度,使得每个维度都相对独立。这样在修改或维护某个维度时,不会对其他维度产生影响,降低了代码的复杂性。

(5)提高了系统的灵活性:通过桥接模式,可以动态地切换和组合不同的抽象部分和实现部分,以满足不同的需求,使得系统更加灵活可配置。

4. 主要缺点

(1)增加了系统的复杂性:桥接模式需要定义抽象部分和实现部分的接口和类,增加了系统的复杂性。当系统的维度较多时,可能需要创建大量的类和接口,导致代码结构复杂。

(2)增加了系统的开销:由于桥接模式需要通过对象组合实现抽象部分和实现部分的桥接,可能会增加一定的对象开销和运行时开销。

(3)对客户端的要求较高:使用桥接模式时,客户端需要了解抽象部分和实现部分的接口和类,以正确组合它们。这要求客户端具有一定的理解和使用桥接模式的能力。

5. 应用场景

桥接模式适用于以下场景:

(1)当你希望将抽象部分和实现部分分离,使它们可以独立地变化时,可以使用桥接模式。这样可以避免在继承关系中产生类爆炸的问题。

(2)当你有多个维度的变化,而且希望能够在运行时动态地组合这些变化时,可以使用桥接模式。例如,如果有多种颜色和多种形状,你希望能够按照需要组合不同的颜色和形状,那么桥接模式可以提供这种灵活性。

(3)当你希望在抽象部分和实现部分之间建立一个稳定的关联关系,并且可以扩展和变化这些部分时,可以使用桥接模式。这样可以避免在抽象和实现之间紧密耦合,使得它们可以独立地发展。

(4)当你希望实现继承的多态性,但又不希望使用继承来实现所有可能的组合时,可以使用桥接模式。桥接模式可以将继承关系转换为对象的组合关系,从而更加灵活地实现多态性。

总之,桥接模式适用于需要将抽象和实现分离、有多个维度的变化、需要建立稳定关联关系和实现多态性的场景。它可以提高系统的灵活性、可扩展性和可维护性。

相关推荐
晨米酱4 小时前
JavaScript 中"对象即函数"设计模式
前端·设计模式
数据智能老司机9 小时前
精通 Python 设计模式——分布式系统模式
python·设计模式·架构
数据智能老司机10 小时前
精通 Python 设计模式——并发与异步模式
python·设计模式·编程语言
数据智能老司机10 小时前
精通 Python 设计模式——测试模式
python·设计模式·架构
数据智能老司机10 小时前
精通 Python 设计模式——性能模式
python·设计模式·架构
使一颗心免于哀伤10 小时前
《设计模式之禅》笔记摘录 - 21.状态模式
笔记·设计模式
数据智能老司机1 天前
精通 Python 设计模式——创建型设计模式
python·设计模式·架构
数据智能老司机1 天前
精通 Python 设计模式——SOLID 原则
python·设计模式·架构
烛阴1 天前
【TS 设计模式完全指南】懒加载、缓存与权限控制:代理模式在 TypeScript 中的三大妙用
javascript·设计模式·typescript
李广坤1 天前
工厂模式
设计模式