简介
门面模式隐藏了系统内部的复杂性,使客户端使用起来变的简单,该设计模式属于结构型设计模式。
适用场景
1、子系统越来越复杂,适用门面模式可以使客户端简单调用;
2、存在多层系统结构,利用门面模式作为每层的入口,简化层间调用;
优点
1、简化调用过程,无需了解子系统,防止带来风险;
2、减少系统依赖,松散耦合;
3、更好的划分访问层次;
4、符合迪米特法则,即最少知道原则;
缺点
1、增加子系统,扩展子系统行为容易引入风险;
2、不符合开闭原则;
示例
门面模式的UML图:
下面看下这几个类的具体实现:
Shape接口:
public interface Shape {
void draw();
}
Circle类,实现了Shape接口
public class Circle implements Shape{
public void draw() {
System.out.println("画圆");
}
}
Rectangle类,实现了Shape接口
public class Rectangle implements Shape{
public void draw() {
System.out.println("画长方形");
}
}
ShapeMaker类,Shape的制造者,就是门面类,客户端都是使用该类。
public class ShapeMaker {
private Circle circle;
private Rectangle rectangle;
public ShapeMaker(){
circle = new Circle();
rectangle = new Rectangle();
}
public void drawCircle(){
circle.draw();
}
public void drawRectangle(){
rectangle.draw();
}
}
Test类,为测试类:
public class Test {
public static void main(String[] args) {
ShapeMaker shapeMaker = new ShapeMaker();
shapeMaker.drawCircle();
shapeMaker.drawRectangle();
}
}
输出结果为:
画圆
画长方形
可以把门面模式抽象为:
源码分析
mybatis中应用
如图,Configuration类封装了复杂度,使客户端调用变的简单,以下示例只是Configuration的部分代码:
public Executor newExecutor(Transaction transaction, ExecutorType executorType) {
executorType = executorType == null ? defaultExecutorType : executorType;
executorType = executorType == null ? ExecutorType.SIMPLE : executorType;
Executor executor;
if (ExecutorType.BATCH == executorType) {
executor = new BatchExecutor(this, transaction);
} else if (ExecutorType.REUSE == executorType) {
executor = new ReuseExecutor(this, transaction);
} else {
executor = new SimpleExecutor(this, transaction);
}
if (cacheEnabled) {
executor = new CachingExecutor(executor);
}
executor = (Executor) interceptorChain.pluginAll(executor);
return executor;
}
tomcat中应用
在tomcat中也有一些门面模式的体现,如RequestFacade
和ResponseFacade
类,从名字上就可以看出来。
@Override
public Object getAttribute(String name) {
if (request == null) {
throw new IllegalStateException(
sm.getString("requestFacade.nullRequest"));
}
return request.getAttribute(name);
}
@Override
public ServletInputStream getInputStream() throws IOException {
if (request == null) {
throw new IllegalStateException(
sm.getString("requestFacade.nullRequest"));
}
return request.getInputStream();
}
封装了复杂性,客户端其实都是调用了RequestFacade的方法。
slf4j中应用
slf4j也使用了门面模式,他把logback,log4j,log4j2,jul等进行了封装,使客户端调用变得很简单,只需要以下代码:
public abstract class AbstractController {
protected Logger logger = LoggerFactory.getLogger(getClass());
}
通过该方法,隐藏了对子系统的复杂性。
本文为博主原创文章,未经博主允许不得转载。
更多内容请访问:IT源点
注意:本文归作者所有,未经作者允许,不得转载