桥接模式大白话讲解
一句话概括
就像遥控器和电器的关系:遥控器(抽象)可以控制各种电器(实现),互相独立变化
现实生活比喻
场景1:遥控器与电器
- 遥控器(抽象):开关、调音量、换台等操作
- 电器(实现):电视、空调、音响等具体设备
- 关系:同一个遥控器可以控制不同电器,同一个电器也可以用不同遥控器
场景2:画笔与颜色
- 画笔(抽象):粗细、形状、材质
- 颜色(实现):红色、蓝色、绿色等
- 关系:同样的画笔可以用不同颜色,同样的颜色可以用不同画笔
完整代码示例
场景:图形绘制系统
java
/**
* 桥接模式 - 图形绘制示例
*/
public class Main {
public static void main(String[] args) {
System.out.println("=== 不同形状使用不同颜色 ===");
// 红色圆形
Color red = new Red();
Shape circle = new Circle(red);
circle.draw();
// 蓝色矩形
Color blue = new Blue();
Shape rectangle = new Rectangle(blue);
rectangle.draw();
// 绿色圆形
Color green = new Green();
Shape greenCircle = new Circle(green);
greenCircle.draw();
System.out.println("\n=== 新增形状和颜色很容易 ===");
// 新增三角形,使用现有颜色
Shape triangle = new Triangle(red);
triangle.draw();
// 新增颜色,用于现有形状
Color yellow = new Yellow();
Shape yellowRectangle = new Rectangle(yellow);
yellowRectangle.draw();
}
}
/**
* 实现化接口 - 颜色
*/
interface Color {
String applyColor();
}
/**
* 具体实现化 - 各种颜色
*/
class Red implements Color {
@Override
public String applyColor() {
return "红色";
}
}
class Blue implements Color {
@Override
public String applyColor() {
return "蓝色";
}
}
class Green implements Color {
@Override
public String applyColor() {
return "绿色";
}
}
class Yellow implements Color {
@Override
public String applyColor() {
return "黄色";
}
}
/**
* 抽象化 - 形状
*/
abstract class Shape {
protected Color color; // 桥接的关键:持有颜色的引用
public Shape(Color color) {
this.color = color;
}
public abstract void draw();
}
/**
* 扩展抽象化 - 具体形状
*/
class Circle extends Shape {
public Circle(Color color) {
super(color);
}
@Override
public void draw() {
System.out.println("绘制" + color.applyColor() + "的圆形");
}
}
class Rectangle extends Shape {
public Rectangle(Color color) {
super(color);
}
@Override
public void draw() {
System.out.println("绘制" + color.applyColor() + "的矩形");
}
}
class Triangle extends Shape {
public Triangle(Color color) {
super(color);
}
@Override
public void draw() {
System.out.println("绘制" + color.applyColor() + "的三角形");
}
}
运行结果
=== 不同形状使用不同颜色 ===
绘制红色的圆形
绘制蓝色的矩形
绘制绿色的圆形
=== 新增形状和颜色很容易 ===
绘制红色的三角形
绘制黄色的矩形
更复杂的例子:消息发送系统
java
/**
* 消息发送系统 - 消息类型和发送方式的桥接
*/
public class MessageExample {
public static void main(String[] args) {
System.out.println("=== 不同类型的消息通过不同方式发送 ===");
// 邮件发送器
MessageSender emailSender = new EmailSender();
// 短信发送器
MessageSender smsSender = new SMSSender();
// 微信发送器
MessageSender wechatSender = new WechatSender();
// 普通消息通过邮件发送
Message normalEmail = new NormalMessage(emailSender);
normalEmail.send("你好,这是普通消息");
// 紧急消息通过短信发送
Message urgentSMS = new UrgentMessage(smsSender);
urgentSMS.send("系统发生严重错误!");
// 普通消息通过微信发送
Message normalWechat = new NormalMessage(wechatSender);
normalWechat.send("今天下午开会");
// 紧急消息通过邮件发送
Message urgentEmail = new UrgentMessage(emailSender);
urgentEmail.send("项目延期通知");
}
}
/**
* 实现化接口 - 消息发送方式
*/
interface MessageSender {
void send(String message);
}
/**
* 具体实现化 - 各种发送方式
*/
class EmailSender implements MessageSender {
@Override
public void send(String message) {
System.out.println("[邮件发送] " + message);
}
}
class SMSSender implements MessageSender {
@Override
public void send(String message) {
System.out.println("[短信发送] " + message);
}
}
class WechatSender implements MessageSender {
@Override
public void send(String message) {
System.out.println("[微信发送] " + message);
}
}
/**
* 抽象化 - 消息类型
*/
abstract class Message {
protected MessageSender sender;
public Message(MessageSender sender) {
this.sender = sender;
}
public abstract void send(String message);
}
/**
* 扩展抽象化 - 具体消息类型
*/
class NormalMessage extends Message {
public NormalMessage(MessageSender sender) {
super(sender);
}
@Override
public void send(String message) {
System.out.print("普通消息 -> ");
sender.send(message);
}
}
class UrgentMessage extends Message {
public UrgentMessage(MessageSender sender) {
super(sender);
}
@Override
public void send(String message) {
System.out.print("紧急消息 -> ");
sender.send("【紧急】" + message);
}
}
运行结果
=== 不同类型的消息通过不同方式发送 ===
普通消息 -> [邮件发送] 你好,这是普通消息
紧急消息 -> [短信发送] 【紧急】系统发生严重错误!
普通消息 -> [微信发送] 今天下午开会
紧急消息 -> [邮件发送] 【紧急】项目延期通知
桥接模式的核心结构
抽象化(Abstraction) ←------------------ 实现化(Implementor)
↑ ↑
扩展抽象化(RefinedAbstraction) 具体实现化(ConcreteImplementor)
关键点:
- 抽象化 持有实现化的引用(桥接)
- 两者可以独立扩展,不影响对方
适用场景(大白话版)
✅ 适合用桥接模式的场景:
-
多个维度的变化
java// 图形(形状) × 颜色 = 多种组合 // 消息(类型) × 发送方式 = 多种组合 // 如果不使用桥接模式,需要为每个组合创建类: // RedCircle, BlueCircle, RedRectangle, BlueRectangle... -
避免永久绑定
java// 不是把形状和颜色硬编码在一起 // 而是在运行时动态组合 Shape shape = new Circle(chooseColor()); // 运行时决定颜色 -
独立扩展
java// 新增形状:Pentagon,不影响颜色 // 新增颜色:Purple,不影响形状 // 两者独立发展
❌ 不适合的场景:
- 变化维度很少(只有1-2种组合)
- 抽象和实现紧密耦合(本来就该在一起)
- 简单的一次性需求
与其它模式对比
| 模式 | 比喻 | 解决什么问题 |
|---|---|---|
| 适配器模式 | 转接头 | 让不兼容的接口能够工作 |
| 桥接模式 | 遥控器与电器 | 让抽象和实现独立变化 |
| 策略模式 | 不同的算法 | 封装可互换的算法 |
桥接模式的威力
传统继承的问题:
Shape
├── RedCircle
├── BlueCircle
├── RedRectangle
├── BlueRectangle
├── RedTriangle
└── BlueTriangle
新增颜色或形状时,类数量爆炸式增长
桥接模式解决:
Shape(抽象) Color(实现)
├── Circle ├── Red
├── Rectangle ├── Blue
└── Triangle └── Green
新增颜色:+1个类,新增形状:+1个类
优缺点
优点:
- 解耦抽象和实现
- 更好的扩展性
- 符合开闭原则
- 隐藏实现细节
缺点:
- 增加复杂度:需要多一层理解
- 设计要求高:需要正确识别出两个独立变化的维度
总结
桥接模式就是:
- 搭桥:在两个独立变化的维度之间建立连接
- 解耦:让抽象部分和实现部分可以独立发展
- 组合:通过组合代替继承,避免类爆炸
核心口诀:
多个维度会变化,
继承爆炸太可怕。
桥接模式来解耦,
抽象实现分开耍!
就像现实中的:
- 🎮 游戏手柄与游戏:同一手柄玩不同游戏,同一游戏用不同手柄
- 🖨️ 打印机与纸张:同一打印机用不同纸张,同一纸张用不同打印机
- 🚗 汽车与引擎:同一车型配不同引擎,同一引擎用于不同车型
- 💳 支付方式与商户 :同一支付方式在不同商户使用,同一商户支持多种支付


记住:当你发现需要在多个维度上扩展,且这些维度会独立变化时,考虑桥接模式!