
外观模式定义
外观模式又称为门面模式,它通过引入一个外观角色来简化客户端与子系统之间的交互,为复杂的子系统调用提供一个统一的入口。
在我们实际的工作中,外观模式是最常用的一种设计模式之一。
外观模式作用
外观模式通过定义一个一致的接口,用以屏蔽内部子系统的细节,使得调用端只需跟这个接口发生调用,而无需关心这个子系统的内部细节,且客户端调用非常方便。
如下图所示:

外观模式是迪米特法则的一种具体实现,通过引入一个新的外观角色可以降低原有系统的复杂度,同时降低客户类与子系统的耦合度。
外观模式的目的:不是给予子系统添加新的功能接口,而是为了让外部减少与子系统内多个模块的交互,松散耦合,从而让外部能够更简单地使用子系统。
外观模式角色
外观模式,包含如下两个角色:

1.Facade外观角色
Facade(外观角色):为多个子系统对外提供一个共同的接口,它将所有从客户端发来的请求委派到相应的子系统去,传递给相应的子系统对象处理。
2.SubSystem子系统角色
SubSystem(子系统角色):实现系统的部分功能,客户可以通过外观角色访问它。
外观模式案例
还是拿图形生成来举例,定义一个图形接口,然后分别定义具体的圆形,长方形和正方形来实现图形接口。
为了让客户端代码更加简单地使用相应的功能接口,而不必了解更多的图形细节,可以通过使用外观模式来实现。

再来看一下具体代码实现:
1.定义Shape接口
public interface Shape {
void draw();
}
2.定义画图实现类
public class Circle implements Shape {
@Override
public void draw() {
System.out.println("Circle::draw()");
}
}
Rectangle 和 Square 类实现和Circle类似,因篇幅原因省略…
3.定义外观类
public class ShapeMaker {
private Shape circle;
private Shape rectangle;
private Shape square;
public ShapeMaker() {
circle = new Circle();
rectangle = new Rectangle();
square = new Square();
}
//画圆
public void drawCircle(){
circle.draw();
}
//画长方形
public void drawRectangle(){
rectangle.draw();
}
//画正方形
public void drawSquare(){
square.draw();
}
}
4.客户端这样使用代码
public class FacadePatternDemo {
public static void main(String[] args){
ShapeMaker shapeMaker = new ShapeMaker();
//客户端只需要和外观类打交道
shapeMaker.drawCircle();
shapeMaker.drawRectangle();
shapeMaker.drawSquare();
}
}
外观模式应用
外观模式是结构型模式,主要用于屏蔽复杂的内部接口,对外提供一个统一的调用方式和类,主要的应用场景分为如下3类:
- 当要为访问一系列复杂的子系统提供一个简单入口时可以使用外观模式;
- 客户端程序与多个子系统之间存在很大的依赖性,引入外观类可以将子系统与客户端解耦,从而提高子系统的独立性和可移植性;
- 在层次化结构中,可以使用外观模式定义系统中每一层的入口,层与层之间不直接产生联系,而通过外观类建立联系,降低层之间的耦合度。
关于mikechen
mikechen睿哥,10年+大厂架构经验,资深技术专家,就职于阿里巴巴、淘宝、百度等一线互联网大厂。