桥接模式(将类的功能层次结构与实现层级结构分离)
用处
- 父类具有基本功能
- 在子类中增加新的功能
为了增加新功能而产生的层次,称为功能层次结构
- 父类通过声明抽象方法来定义API
- 子类通过实现具体方法来实现API
为了实现父类与子类的任务分担,称为实现层次结构
桥接模式的作用,就是将类的功能层次结构与实现层级结构分离。
角色
- Abstraction(抽象化)
该角色位于”类的功能层次结构“的最上层。它使用Implementor角色的方法定义了基本的功能。该角色中保存了Implementor角色的实例 - RefinedAbstraction(改善后的抽象化)
在Abstraction角色的基础上增加了新功能的角色。 - Implementor(实现者)
该角色位于”类的实现层次结构“的最上层。它定义了用于实现Abstraction角色的API的方法 - ConcreteImplementor(具体实现者)
该角色负责实现在Implementor角色中定义的API。
类图
-
左侧是功能层次结构,右侧是实现层次结构,中间由一个依赖关系像桥一样连接两个结构,因此称为桥接模式
-
继承Abstraction抽象类的子类RefinedAbstraction类用于功能扩展(新加方法),RefinedAbstraction类也通过抽象类聚合了ConcreteImplementor,可以让方法有不同的具体实现。
举例
public class Main {
public static void main(String[] args) {
Display d1 = new Display(new StringDisplayImpl("Hello,China."));
Display d2 = new CountDisplay(new StringDisplayImpl("Hello world"));
CountDisplay d3 = new CountDisplay(new StringDisplayImpl("Hello,Universe."));
d1.display();
d2.display();
d3.display();
d3.multiDisplay(5);
}
}
//Abstraction角色
class Display{
private DisplayImpl impl;
public Display(DisplayImpl impl){
this.impl = impl;
}
public void open(){
impl.rawOpen();
}
public void close(){
impl.rawClose();
}
public void print(){
impl.rawPrint();
}
public final void display(){
open();
print();
close();
}
}
//RefinedAbstracion角色
class CountDisplay extends Display{
public CountDisplay(DisplayImpl impl){
super(impl);
}
public void multiDisplay(int times){
open();
for(int i = 0 ; i < times;i++){
print();
}
close();
}
}
//Implementor角色
abstract class DisplayImpl{
public abstract void rawOpen();
public abstract void rawPrint();
public abstract void rawClose();
}
//ConcreteImplementor角色
class StringDisplayImpl extends DisplayImpl{
private String string;
private int width;
public StringDisplayImpl(String string) {
this.string = string;
this.width = string.getBytes().length;
}
@Override
public void rawOpen() {
printLine();
}
@Override
public void rawPrint() {
System.out.println("|"+string+"|");
}
@Override
public void rawClose() {
printLine();
}
private void printLine(){
System.out.print("+");
for(int i = 0 ; i<width;i++){
System.out.print("-");
}
System.out.println("+");
}
}
- 如果需要增加功能(方法),则继承Display抽象类或其子类,新增新的方法
- 如果需要增加新的实现,则继承DisplayImpl抽象类,并重写方法。
总结
- 符合开闭原则,扩展性极强
- 用于分离类的功能层次结构和实现层次结构,并独立的进行扩展。
- 继承是强关联,而委托是弱关联,在举例中的Display类中使用了委托,将任务委托给DisplayImpl类(调用DisplayImpl方法)。