外观模式(Facade)
定义
定义了一个高层、统一的接口,外部与通过这个统一的接口对子系统中的一群接口进行访问。
优缺点
优点
- 实现客户类与子系统类的松耦合
- 降低原有系统的复杂度
提高了客户端使用的便捷性,使得客户端无须关心子系统的工作细节,通过外观角色即可调用相关功能。
(1)引入外观角色之后,用户只需要与外观角色交互;
(2)用户与子系统之间的复杂逻辑关系由外观角色来实现
缺点
- 在不引入抽象外观类的情况下,增加新的子系统可能需要修改外观类或客户端的源代码,违背了“开闭原则”
- 不能很好地限制客户使用子系统类,如果对客户访问子系统类做太多的限制则减少了可变性和灵活性。
改进-抽象外观模式
可以参考 https://www.beibq.cn/book/7jvf266-9281
感觉,抽象外观模式有些得不偿失
优点
- 不违反开闭原则
缺点
代码冗余
可能新外观类大部分代码和旧的一样,造成代码冗余
引入新外观类
需求不断变化,那么需要不停引入新外观类,麻烦
外观类使用变复杂
毕竟需要动态的引用外观类,用户使用的方式可能要通过获取线上配置等方式再利用反射创建对应类。
应用场景
- 要为一个复杂的子系统对外提供一个简单的接口
- 提供子系统的独立性
- 客户程序与多个子系统之间存在很大的依赖性
- 引入外观类将子系统与客户以及其他子系统解耦,可以提高子系统的独立性和可移植性。
- 在层次化结构中,可以使用外观模式定义系统中每一层的入口层与层之间不直接产生联系,而通过外观类建立联系,降低层之间的耦合度
举例
吃瓜群众想知道程序猿日常一天怎么度过
程序猿的相关类
public class Morning {
public void washFace(){
System.out.println("------洗脸------");
}
public void clothing(){
System.out.println("------换衣服------");
}
public void toothbrushing(){
System.out.println("------刷牙------");
}
public void breakfast(){
System.out.println("------吃早餐------");
}
}
public class DayTime {
public void coding(){
System.out.println("---写代码---嗒嗒嗒---嗒嗒嗒");
}
public void lunch(){
System.out.println("-----吃午饭-----");
}
public void nooning(){
System.out.println("-----午休-呼噜~呼噜~~~");
}
public void supper(){
System.out.println("-----吃晚饭-----");
}
}
public class NightLife {
public void bathing(){
System.out.println("-----洗澡-----");
}
public void gaming(){
System.out.println("-----打游戏-----");
}
public void sleep(){
System.out.println("-----睡觉~呼噜~呼噜-----");
}
}
外观类作为中介,介绍程序猿一天
public class ProgramerLifeFacade {
public void programerLife(){
getup();
System.out.println();
work();
System.out.println();
nightLife();
}
private void getup(){
System.out.println("===========早上起床==========");
Morning morning = new Morning();
morning.toothbrushing();
morning.washFace();
morning.clothing();
morning.breakfast();
}
private void work(){
System.out.println("===========白天工作==========");
DayTime dayTime = new DayTime();
dayTime.coding();
dayTime.coding();
dayTime.lunch();
dayTime.nooning();
dayTime.coding();
dayTime.coding();
dayTime.supper();
dayTime.coding();
dayTime.coding();
}
private void nightLife(){
System.out.println("===========下班夜生活==========");
NightLife night = new NightLife();
night.bathing();
night.gaming();
night.sleep();
}
}
吃瓜群众查看程序猿日常
public class Client {
public static void main(String args[]){
ProgramerLifeFacade programerLife = new ProgramerLifeFacade();
programerLife.programerLife();
}
}
查看结果:
===========早上起床==========
------刷牙------
------洗脸------
------换衣服------
------吃早餐------
===========白天工作==========
---写代码---嗒嗒嗒---嗒嗒嗒
---写代码---嗒嗒嗒---嗒嗒嗒
-----吃午饭-----
-----午休-呼噜~呼噜~~~
---写代码---嗒嗒嗒---嗒嗒嗒
---写代码---嗒嗒嗒---嗒嗒嗒
-----吃晚饭-----
---写代码---嗒嗒嗒---嗒嗒嗒
---写代码---嗒嗒嗒---嗒嗒嗒
===========下班夜生活==========
-----洗澡-----
-----打游戏-----
-----睡觉~呼噜~呼噜-----