本文目的在於對比分析Adaptor,Decorator,Facade這三種設計模式的差異,加深對這幾種設計模式的理解。
模式 | 說明 |
Adaptor | 把接口A的具體實現轉換成對接口B的實現,以實現對B接口調用的客戶能使用A提供的功能。 |
Decorator | 封裝原來的接口A實現類,動態增加額外的功能,實現對原有實現類功能的擴展。 |
Facade | 爲複雜的子系統提供抽象簡單的接口,使用方調用接口,而不用關注子系統內部的複雜邏輯。 |
Adaptor 適配器模式
適配器模式使兩個不相關的接口一起工作。在真實的工作場景中,會出現一個客戶端依賴B接口的實現類,但需要使用A接口的功能滿足客戶端的需要。適配器模式就能夠實現使A,B兩個不相關的接口一起工作,把對A接口功能的實現類轉化成對B接口功能的實現。
demo的類圖如下:
public interface Duck {
public void quack();
}
public interface Goose {
public void cackle();
}
public class WightGoose implements Goose {
@Override
public void cackle() {
System.out.println("cackle");
}
}
public class GooseToDuckAdapter implements Duck {
private Goose goose;
public GooseToDuckAdapter(Goose goose) {
this.goose = goose;
}
@Override
public void quack() {
goose.cackle();
}
}
public class Client {
public static void main(String[] args){
Goose goose = new WightGoose();
Duck duck = new GooseToDuckAdapter(goose);
duck.quack();
}
}
Decorator 裝飾者模式
裝飾者模式也可以叫靜態代理,對接口的實現類,可以在不更改原有實現類邏輯的基礎上靜態地擴展原有實現類功能,實現對額外邏輯增加代碼,而不是更改代碼。
demo類圖:
public class GreenDuck implements Duck{
@Override
public void quack() {
System.out.println("green Duck quack!");
}
}
public class SmartDuck implements Duck {
private Duck duck;
public SmartDuck(Duck duck) {
this.duck = duck;
}
@Override
public void quack() {
System.out.println("become Smarter");
duck.quack();
System.out.println("louder and sweet!");
}
}
public class Client {
public static void main(String[] args){
Duck duck = new GreenDuck();
duck.quack();
System.out.println();
Duck smartDuck = new SmartDuck(duck);
smartDuck.quack();
}
}
Facade 門面模式
門面模式隱藏複雜系統的內部結構和實現細節,爲複雜的系統提供對外使用的簡單方便的調用接口,使複雜系統的功能更簡單使用,理解以及測試,同時減少外部系統對該複雜系統的依賴。
不用Facade實現demo:
public class AirConditioner {
public void turnOn(){
System.out.println("AirConditioner on!");
}
public void turnOff(){
System.out.println("AirConditioner off!");
}
}
public class Audio {
public void musicOn(){
System.out.println("Music on!");
}
public void musicOff(){
System.out.println("Music off!");
}
}
public class Curtain {
public void openCurtain(){
System.out.println("open Curtain!");
}
public void closeCurtain(){
System.out.println("close Curtain!");
}
}
public class Light {
public void ligntOn(){
System.out.println("turn Light on!");
}
public void ligntOff(){
System.out.println("turn Light off!");
}
}
public class ClientWithNoFacade {
public static void main(String[] args){
System.out.println("When I coming home,I do ");
AirConditioner airConditioner = new AirConditioner();
Audio audio = new Audio();
Curtain curtain = new Curtain();
Light light = new Light();
airConditioner.turnOn();
audio.musicOn();
curtain.openCurtain();
light.ligntOn();
System.out.println("When I am out,I need to do ");
airConditioner.turnOff();
audio.musicOff();
curtain.closeCurtain();
light.ligntOff();
}
}
使用Facade demo:
public class HomeFacade {
private AirConditioner airConditioner;
private Audio audio;
private Curtain curtain;
private Light light;
public HomeFacade() {
airConditioner = new AirConditioner();
audio = new Audio();
curtain = new Curtain();
light = new Light();
}
public void turnOn(){
System.out.println("HomeFacade do");
airConditioner.turnOn();
audio.musicOn();
curtain.openCurtain();
light.ligntOn();
}
public void turnOff(){
System.out.println("HomeFacade do");
airConditioner.turnOff();
audio.musicOff();
curtain.closeCurtain();
light.ligntOff();
}
}
public class ClientWithFacade {
public static void main(String[] args){
HomeFacade homeFacade = new HomeFacade();
System.out.println("when I coming home");
homeFacade.turnOn();
System.out.println();
System.out.println("When I leaving");
homeFacade.turnOff();
}
}