什么是外观模式
为一个复杂的系统提供了一个简化的接口。通过这种方式,可以隐藏系统的复杂性,并对外提供一个更易于使用的统一接口。外观模式的主要目的是简化客户端与子系统之间的交互,使得客户端不需要直接与复杂的子系统组件进行沟通。
结构
- 外观(Facade)角色:为多个子系统对外提供一个共同的接口。
- 子系统(Sub System)角色:实现系统的部分功能,客户可以通过外观角色访问它。
UML类图
代码理解
// 子系统类1
class SubSystemOne {public void operationOne() {System.out.println("SubSystemOne operationOne()");}
}// 子系统类2
class SubSystemTwo {public void operationTwo() {System.out.println("SubSystemTwo operationTwo()");}
}// 子系统类3
class SubSystemThree {public void operationThree() {System.out.println("SubSystemThree operationThree()");}
}// 外观类
class Facade {private SubSystemOne subSystemOne;private SubSystemTwo subSystemTwo;private SubSystemThree subSystemThree;public Facade() {this.subSystemOne = new SubSystemOne();this.subSystemTwo = new SubSystemTwo();this.subSystemThree = new SubSystemThree();}// 提供一个方法,客户端可以通过这个方法来执行操作public void operation() {System.out.println("Facade operation()");subSystemOne.operationOne();subSystemTwo.operationTwo();subSystemThree.operationThree();}
}// 客户端类
public class Client {public static void main(String[] args) {Facade facade = new Facade();facade.operation();}
}
优缺点
优点
- 外观模式提供了一个简化的接口,客户端可以通过这个接口访问复杂的子系统,而不需要了解子系统内部的复杂性。
- 客户端与子系统解耦,客户端不需要知道子系统内部的实现细节,只需要与外观类交互,这降低了它们之间的耦合度。
- 通过外观类可以控制对子系统内部功能的访问,隐藏内部实现,只暴露必要的操作给客户端,增加了系统的安全性。
- 外观模式使得客户端只需要与外观类交互,减少了客户端与子系统之间的交互,符合迪米特法则(最少知道原则)。
缺点
- 引入外观类可能会增加系统的复杂度,因为需要额外的类来封装子系统。
- 如果子系统中添加了新的功能,可能需要修改外观类以提供新的接口,这违反了开闭原则(软件实体应当对扩展开放,对修改封闭)。
使用场景
- 当一个子系统非常复杂,拥有许多不同的操作和组件时,使用外观模式可以为客户端提供一个简单的接口,隐藏子系统的复杂性。
- 在多层架构系统中,如表示层、业务逻辑层和数据访问层,外观模式可以作为每一层的入口点,简化层与层之间的通信。
- 如果客户端代码需要与多个子系统组件交互,而这些组件的使用又很复杂,可以通过外观模式减少客户端代码的复杂性。