JavaScript 設計模式(四):適配者模式

適配器模式

適配器模式:將一個類(對象)的接口(方法或屬性)轉化成客戶希望的另外一個接口(方法或屬性),使得原本由於接口不兼容而不能一起工作的那些類(對象)可以正常協作。簡單理解就是爲兼容而生的 “轉換器”。

對於強迫症患者,那麼多形狀各異的接口,對應着不同數據線。如果可以有一個轉接口實現集合兼容,豈不美哉。沒錯,這樣一個適配器,你值得擁有。(各大廠商加把勁。。。)

生活小栗子:

  1. 港式插頭轉換器
  2. 筆記本電源適配器
  3. Type-C 轉接口

模式特點

  1. 新包裝對象(適配器對象)實現對原對象接口的訪問(接口名可不同)
  2. 適配器對象不對請求數據做預處理,直接傳入原對象接口處理
  3. 適配器對象對外接口名統一,外部調用者可統一接口調用多對象方法

模式實現

實現方式:在不改變原有對象接口的基礎上,定義一個包裝對象,新對象轉接調用原有接口,使外部調用者可以正常使用。

第三方SDK的應用

// 適配器實現地圖SDK統一渲染
var googleMap = {
    show: function(){
        console.log('開始渲染谷歌地圖');
    }
};
var baiduMap = {
    display: function(){
        console.log('開始渲染百度地圖');
    }
};

// 外部實際調用的適配器對象
var baiduMapAdapter = {
    show: function() {
        return baiduMap.display();
    }
};

// 外部調用者
var renderMap = function(map) {
    map.show();   // 統一接口調用
};

renderMap(googleMap);
renderMap(baiduMapAdapter);

ES6實現適配器

// 使用ES6改寫適配器實現地圖SDK統一渲染
class googleMap {
  show() {
    console.log('開始渲染谷歌地圖');
  }
}

class baiduMap {
  display() {
    console.log('開始渲染百度地圖');
  }
}

class baiduMapAdapter extends baiduMap {
  constructor() {
    super();
  }

  show() {
    this.display();
  }
}

// 外部調用者
function renderMap(map) {
  map.show();   // 統一接口調用
}

renderMap(new googleMap());
renderMap(new baiduMapAdapter());

jQuery中的應用

適配器模式非常適用於跨瀏覽器兼容,例如強大的 jQuery 封裝了事件處理的適配器,解決跨瀏覽器兼容性問題,極大簡化我們日常編程操作。

// $('selector').on 的實現
function on(target, event, callback) {
    if (target.addEventListener) {
        // 標準事件監聽
        target.addEventListener(event, callback);
    } else if (target.attachEvent) {
        // IE低版本事件監聽
        target.attachEvent(event, callback)
    } else {
        // 低版本瀏覽器事件監聽
        target[`on${event}`] = callback
    }
}

適用場景

  1. 跨瀏覽器兼容
  2. 整合第三方SDK
  3. 新老接口兼容

適配器模式的初衷是爲了解決多對象(接口)兼容問題,如果存在多對象協同工作時,不方便直接修改原對象的基礎上,可考慮用適配器封裝,以便外部調用者統一使用。

與其它模式的異同

適配器模式不會改變原有接口,這一點與裝飾者模式和代理模式類似。

VS 代理模式

適配器模式與代理模式最相似,同樣都是創建一個新對象(包裝一次),實現對本體的調用。

兩者的區別:代理模式是爲了管控原有對象(本體)的訪問,代理的初衷並不是爲兼容,並主張代理與本體對外接口保持一致。

而適配器則是爲兼容而生的 “轉換器”,並不預處理請求,直接將請求轉接給原接口,新接口與原接口名可能不同。

“代理模式“(嚴父):學校繳費要一千塊,這麼多?
"適配器模式” (慈母):學校繳費要一千塊,給給給。

裝飾者模式及外觀模式,會在之後的篇章整理,這裏稍作了解。

VS 裝飾者模式

裝飾者模式的作用是爲對象添加功能,可添加多次,形成裝飾鏈。而適配器只會對原有對象包裝一次。

VS 外觀模式

外觀模式與適配器模式最大的區別,是定義了一個新的接口。

優缺點

  • 優點:兼容性,保證外部可統一接口調用
  • 缺點:額外對象的創建,非直接調用,存在一定的開銷(且不像代理模式在某些功能點上可實現性能優化)。

參考文章

本文首發Github,期待Star!
https://github.com/ZengLingYong/blog

作者:以樂之名
本文原創,有不當的地方歡迎指出。轉載請指明出處。
發表評論
所有評論
還沒有人評論,想成為第一個評論的人麼? 請在上方評論欄輸入並且點擊發布.
相關文章