桥接模式-简介
桥接模式(Bridge Pattern)是用于把抽象化与实现化解耦,使得二者可以独立变化。这种类型的设计模式属于结构型模式,它通过提供抽象化和实现化之间的桥接结构,来实现二者的解耦。
它通过组合的方式,而不是继承的方式,将抽象和实现的部分连接起来。
将抽象和实现分离,是它们可以独立变化。它是用组合关系替代继承关系来实现,从而降低了抽象和实现这两个可变维度的耦合。
为什么需要桥接模式
举个例子:
现在有如下需求,需要创建不同的图形,并且每个图形有不同的形状,也可能会有不同的颜色,如果我们采用继承的方式来实现这个需求,如下图所示:
其实我们可以发现,利用这种继承模式来实现,类似于一个线性继承结构,如果说有 x 种形状,y 种颜色,那么我们最多会有 x * y 个子类,这样的话,非常容易产生子类爆炸的情况,拓展起来非常不灵活。
在这个需求中,有多个不同的维度(形状、颜色),为了设计更加灵活的系统,我们此时考虑桥接模式,用组合关系替代继承关系。
桥接模式-组成结构
- 抽象化角色(Abstraction):定义抽象类,并包含一个对实现化对象的引用。
- 拓展抽象化角色(Refined Abstraction):是抽象化角色的子类,实现父类中的业务方法,并且通过组合的关系调用实现化角色中的业务方法。
- 实现化角色(Implementor):定义实现化角色的接口,供扩展抽象化角色调用。
- 具体实现化角色(Concrete Implementor):给出实现化角色接口的具体实现。
代码示例
我们完善上述 图形 的案例。
Shape - 抽象化角色(Abstraction)
Circle、Rectangle - 拓展抽象化角色(Refined Abstraction)
Color - 实现化角色(Implementor)
Red、Blue、Green - 具体实现化角色(Concrete Implementor)
java
public abstract class Shape {
private Color color;
public Shape(Color color) {
this.color = color;
}
public abstract void getDesc();
public Color getColor() {
return color;
}
public void setColor(Color color) {
this.color = color;
}
}
public class Circle extends Shape{
public Circle(Color color) {
super(color);
}
@Override
public void getDesc() {
System.out.println("This is " + super.getColor().getColor() + " Circle");
}
}
public class Rectangle extends Shape{
public Rectangle(Color color) {
super(color);
}
@Override
public void getDesc() {
System.out.println("This is " + super.getColor().getColor() + " Rectangle");
}
}
public interface Color {
String getColor();
}
public class Red implements Color{
@Override
public String getColor() {
return "Red";
}
}
public class Blue implements Color{
@Override
public String getColor() {
return "Blue";
}
}
public class Green implements Color{
@Override
public String getColor() {
return "Green";
}
}
public class Main {
public static void main(String[] args) {
Color color = new Red();
Shape shape = new Circle(color);
shape.getDesc();
color = new Blue();
shape = new Circle(color);
shape.getDesc();
shape = new Rectangle(color);
shape.getDesc();
}
}
总结
- 桥接模式提高了系统的可拓展性,在两个变化维度中任意拓展一个维度,都不需要修改原有的系统。
- 实现细节对客户透明。
具体使用场景:
- 当一个类存在两个独立变化的维度,且这两个维度都需要进行拓展的时候。
- 当一个系统不希望使用继承或者因为多层次继承导致系统类的个数急剧增加的时候。
- 当一个系统需要在构件的抽象化角色和具体化角色之间增加更多的灵活性的时候,避免在两个层次之间建立静态的继承联系,通过桥接模式可以使它们在抽象层建立一个关联关系。