hooyantsing's Blog

P66 桥接模式-手机问题

字数统计: 730阅读时长: 3 min
2020/11/10

尚硅谷Java设计模式(图解+框架源码剖析)

本节涉及P66~P68内容。

传统方式遇到的问题

1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
50
51
52
classDiagram
class Phone{
+call() void
}
class Folded{
+call() void
}
class UpRight{
+call() void
}
class Silde{
+call() void
}
class Huawei1{
+call() void
}
class Vivo1{
+call() void
}
class Xiaomi1{
+call() void
}
class Huawei2{
+call() void
}
class Vivo2{
+call() void
}
class Xiaomi2{
+call() void
}
class Huawei3{
+call() void
}
class Vivo3{
+call() void
}
class Xiaomi3{
+call() void
}
Phone <|-- Folded
Phone <|-- UpRight
Phone <|-- Silde
Folded <|-- Huawei1
Folded <|-- Vivo1
Folded <|-- Xiaomi1
UpRight <|-- Huawei2
UpRight <|-- Vivo2
UpRight <|-- Xiaomi2
Silde <|-- Huawei3
Silde <|-- Vivo3
Silde <|-- Xiaomi3

可以看到“手机类型”和“手机品牌”十分臃肿,每增加一种“手机类型”,都会导致重复创建新的“手机品牌”类,m*n 最后造成“类爆炸”。使用桥接模式可以将类的数量减少至 m+n 的等级。

桥接模式 Bridge

1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
classDiagram
class Brand{
<<interface>>
+call() void
}
class Vivo
class Xiaomi
class Phone{
<<abstract>>
-Brand brand
}
class FoldPhone
class UpRightPhone
class Client
Brand <|.. Vivo
Brand <|.. Xiaomi
Phone <|-- FoldPhone
Phone <|-- UpRightPhone
Phone o-- Brand
Phone <.. Client
代码实现

行为实现的接口

1
2
3
4
5
public interface Brand {
void open();
void close();
void call();
}

行为具体实现A

1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
public class Xiaomi implements Brand {
@Override
public void open() {
System.out.println("小米手机开机");
}

@Override
public void close() {
System.out.println("小米手机关机");
}

@Override
public void call() {
System.out.println("小米手机打电话");
}
}

行为具体实现B

1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
public class Vivo implements Brand {
@Override
public void open() {
System.out.println("Vivo手机开机");
}

@Override
public void close() {
System.out.println("Vivo手机关机");
}

@Override
public void call() {
System.out.println("Vivo手机打电话");
}
}

Phone和Brand是聚合关系

1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
public abstract class Phone {
private Brand brand;
public Phone(Brand brand){
this.brand = brand;
}

public void open() {
brand.open();
}

public void close() {
brand.close();
}

public void call() {
brand.call();
}
}

抽象类的子类

折叠手机:

1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
public class FoldPhone extends Phone {
public FoldPhone(Brand brand) {
super(brand);
}

@Override
public void open() {
super.open();
System.out.println("折叠手机");
}

@Override
public void close() {
super.close();
System.out.println("折叠手机");
}

@Override
public void call() {
super.call();
System.out.println("折叠手机");
}
}

直立手机:

1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
public class UpRightPhone extends Phone {
public UpRightPhone(Brand brand) {
super(brand);
}

@Override
public void open() {
super.open();
System.out.println("直立手机");
}

@Override
public void close() {
super.close();
System.out.println("直立手机");
}

@Override
public void call() {
super.call();
System.out.println("直立手机");
}
}

桥接模式调用者

使用时,从Phone的继承类里选一个,从Brand的实现类里选一个,组合成想要的手机。

1
2
3
4
5
6
7
8
9
10
11
12
13
public class Client {
public static void main(String[] args) {
Phone xiaomiPhone = new FoldPhone(new Xiaomi());
xiaomiPhone.open();
xiaomiPhone.call();
xiaomiPhone.close();

Phone vivoPhone = new UpRightPhone(new Vivo());
vivoPhone.open();
vivoPhone.call();
vivoPhone.close();
}
}

执行结果:

小米手机开机
折叠手机
小米手机打电话
折叠手机
小米手机关机
折叠手机
Vivo手机开机
直立手机
Vivo手机打电话
直立手机
Vivo手机关机
直立手机

CATALOG
  1. 1. 传统方式遇到的问题
  2. 2. 桥接模式 Bridge
    1. 2.1. 代码实现