【適配器設(shè)計(jì)模式(Adapter Pattern)詳解】Java/Python/Go/JS不同語(yǔ)言實(shí)現(xiàn)

簡(jiǎn)介

適配器模式(Adapter Pattern)是一種結(jié)構(gòu)型設(shè)計(jì)模式,為兩個(gè)不兼容的接口之間架設(shè)橋梁,使不兼容的對(duì)象能夠相互合作。

當(dāng)你希望使用某個(gè)類(lèi),但是其接口與其他代碼不兼容時(shí),可以使用適配器類(lèi)。當(dāng)你需要復(fù)用類(lèi)的共同方法,但是這些共同的方法不是所有子類(lèi)的共性,你可以通過(guò)適配器模式來(lái)兼容。

作用

  1. 將一個(gè)類(lèi)的接口轉(zhuǎn)換成另外一個(gè)接口。
  2. 使得原本不兼容的接口也能一同工作。

實(shí)現(xiàn)步驟

  1. 有一些可以重復(fù)使用的類(lèi),這些類(lèi)不一定有一致的接口。
  2. 建立接口轉(zhuǎn)換類(lèi),將不同的類(lèi)插入到轉(zhuǎn)換類(lèi)中。
  3. 通過(guò)轉(zhuǎn)換類(lèi)來(lái)實(shí)現(xiàn)(繼承或依賴)不同接口的調(diào)用。

UML

adapter-pattern.png

代碼

基礎(chǔ)接口類(lèi)

// MediaPlayer.java 定義視頻/音頻的格式播放接口
public interface MediaPlayer {
  public void play();
  public void setFileType(String fileType);
  public void setFilePath(String filePath);
}

具體播放器實(shí)現(xiàn)類(lèi),可以多個(gè)

// AudioPlayer.java 支持多種音頻格式播放,相對(duì)簡(jiǎn)單,不區(qū)分格式
public class AudioPlayer implements MediaPlayer {
  private String fileType;
  private String filePath;

  public AudioPlayer(String fileType, String filePath) {
    this.fileType = fileType;
    this.filePath = filePath;
  }

  public void play() {
    System.out.println("AudioPlayer fileType:" + fileType + " | filePath:" + filePath);
    if (fileType.equals("mp3")) {
      System.out.println("AudioPlayer::play() mp3");
    } else if (fileType.equals("mp4")) {
      System.out.println("AudioPlayer::play() mp4");
    }
  }
}
// HlsPlayer.java 播放器實(shí)現(xiàn)了視頻接口
public class HlsPlayer implements MediaPlayer {
  private String fileType;
  private String filePath;

  public HlsPlayer(String fileType, String filePath) {
    this.fileType = fileType;
    this.filePath = filePath;
  }

  public void play() {
    System.out.println("HlsPlayer fileType:" + fileType + " | filePath:" + filePath);
    System.out.println("HlsPlayer::play()");
  }
}
// Mp4Player.java 播放器實(shí)現(xiàn)了視頻接口
public class Mp4Player implements MediaPlayer {
  private String fileType;
  private String filePath;

  public Mp4Player(String fileType, String filePath) {
    this.fileType = fileType;
    this.filePath = filePath;
  }

  public void play() {
    System.out.println("Mp4Player fileType:" + fileType + " | filePath:" + filePath);
    System.out.println("Mp4Player::play()");
  }
}

適配器類(lèi)

// PlayerAdapter.java 適配器類(lèi),可以播放各種音頻和視頻,外部調(diào)用方式一樣。適配器也可以實(shí)現(xiàn)基礎(chǔ)播放接口
public class PlayerAdapter implements MediaPlayer {

  private String mediaType;
  private String fileType;
  private String filePath;
  private MediaPlayer mp4Player;
  private MediaPlayer hlsPlayer;
  private MediaPlayer audioPlayer;

  public PlayerAdapter(String mediaType, String fileType, String filePath) {
    this.mediaType = mediaType;
    this.fileType = fileType;
    if (mediaType.equals("video")) {
      if (fileType.equals("mp4")) {
        setMp4Player(fileType, filePath);
      } else if (fileType.equals("hls")) {
        setHlsPlayer(fileType, filePath);
      }
    } else if (mediaType.equals("audio")) {
      setAudioPlayer(fileType, filePath);
    }
  }

  public void setMp4Player(String fileType, String filePath) {
    if (mp4Player == null) {
      mp4Player = new Mp4Player(fileType, filePath);
    } else {
      mp4Player.setFileType(fileType);
      mp4Player.setFilePath(filePath);
    }
  }

  public void setHlsPlayer(String fileType, String filePath) {
    if (hlsPlayer == null) {
      hlsPlayer = new HlsPlayer(fileType, filePath);
    } else {
      hlsPlayer.setFileType(fileType);
      hlsPlayer.setFilePath(filePath);
    }
  }

  public void setAudioPlayer(String fileType, String filePath) {
    if (audioPlayer == null) {
      audioPlayer = new AudioPlayer(fileType, filePath);
    } else {
      audioPlayer.setFileType(fileType);
      audioPlayer.setFilePath(filePath);
    }
  }

  // 通用的適配接口
  public void play() {
    if (this.mediaType.equals("audio")) {
      audioPlayer.play();
    } else if (this.mediaType.equals("video")) {
      if (this.fileType.equals("mp4")) {
        mp4Player.play();
      } else if (this.fileType.equals("hls")) {
        hlsPlayer.play();
      }
    }
  }

  public void setFileType(String fileType) {
    this.fileType = fileType;
  }

  public String getFileType() {
    return fileType;
  }

  public void setFilePath(String filePath) {
    this.filePath = filePath;
  }

  public String getFilePath() {
    return filePath;
  }
}

測(cè)試調(diào)用


    /**
     * 適配器模式是當(dāng)調(diào)用方需需調(diào)用不同功能,但接口并不兼容時(shí),
     * 這時(shí)候可通過(guò)一個(gè)適配器類(lèi)來(lái)做適配,讓調(diào)用方通過(guò)適配類(lèi)再去調(diào)用各個(gè)對(duì)象的功能。
     * 調(diào)用方只知道適配器,而不知道后面的其他對(duì)象。
     */

    // mp4播放
    PlayerAdapter playerAdapter1 = new PlayerAdapter("video", "mp4", "d:/video.mp4");
    playerAdapter1.play();
    // 復(fù)用實(shí)例播音頻
    playerAdapter1.play("audio", "mp4", "d:/audio.mp4");

    // hls播放
    PlayerAdapter playerAdapter2 = new PlayerAdapter("video", "hls", "http://video.m3u8");
    playerAdapter2.play();

    // mp3播放
    PlayerAdapter playerAdapter3 = new PlayerAdapter("audio", "mp3", "d:/audio.mp3");
    playerAdapter3.play();

    // mp4音頻播放
    PlayerAdapter playerAdapter4 = new PlayerAdapter("audio", "mp4", "d:/audio.mp4");
    playerAdapter4.play();
    // 復(fù)用實(shí)例播視頻
    playerAdapter4.play("video", "hls", "d:/video.m3u8");

更多語(yǔ)言版本

image.png

不同語(yǔ)言實(shí)現(xiàn)設(shè)計(jì)模式:https://github.com/microwind/design-pattern

最后編輯于
?著作權(quán)歸作者所有,轉(zhuǎn)載或內(nèi)容合作請(qǐng)聯(lián)系作者
【社區(qū)內(nèi)容提示】社區(qū)部分內(nèi)容疑似由AI輔助生成,瀏覽時(shí)請(qǐng)結(jié)合常識(shí)與多方信息審慎甄別。
平臺(tái)聲明:文章內(nèi)容(如有圖片或視頻亦包括在內(nèi))由作者上傳并發(fā)布,文章內(nèi)容僅代表作者本人觀點(diǎn),簡(jiǎn)書(shū)系信息發(fā)布平臺(tái),僅提供信息存儲(chǔ)服務(wù)。

相關(guān)閱讀更多精彩內(nèi)容

友情鏈接更多精彩內(nèi)容