适配器模式:一招搞定接口不兼容

一、概要

适配器模式(Adapter Pattern)是一种结构型设计模式,它允许将一个类的接口转换成客户端所期望的另一个接口,使得原本由于接⼝不兼容⽽不能⼀起⼯作的那些类可以⼀起⼯作。通俗来讲,就是通过适配器来连接两个不兼容的接口,让客户端通过调用一个通用的接口,而间接实现对其他功能接口的调用。打个形象的比喻,适配器就好比我们生活中的三充数据线,可以适配不同的充电接口。

如何实现?

举个实际案例,我有一个播放器接口Player以及它的实现类MediaPlayer,当前它的功能有限,只允许播放MP3音频文件。另有一个VideoPlayer接口和其实现Mp4Player,是用于播放MP4视频文件的,但是该接口不开放给客户端直接调用。如果现在我要让Player可以支持MP4视频播放,要如何实现呢?

适配器模式:一招搞定接口不兼容_第1张图片

为了解决这个问题,我们就可以引入适配器模式,客户端仍然调用Player接口,然后通过适配器将调用转发到VideoPlayer接口上,以达到播放MP4的目的。

适配器模式:一招搞定接口不兼容_第2张图片

优点

  • 解决接口不兼容问题:适配器模式能够解决不同类之间接口不兼容的问题。通过适配器,客户端可以使用期望的接口,而不需要修改现有的代码或对象。
  • 复用现有的类:适配器模式可以复用已有的类,而无需修改其代码。通过适配器,可以将现有的类包装起来,以适应新的接口。
  • 增加类的透明性:适配器模式使得客户端无需关注被适配的类的具体实现细节,只需要通过适配器与其交互。
  • 灵活性和扩展性:适配器模式可以在不影响现有代码的情况下添加新的适配器类,从而实现对新接口的适配,提高系统的灵活性和扩展性。

缺点

  • 增加了系统的结构复杂性:因为需要引入新的类和对象,过多的适配器可能导致代码混乱和难以维护。
  • 可能引入性能损耗:适配器模式可能会引入额外的性能损耗,因为在转换接口时需要进行额外的处理和转换操作。在性能敏感的系统中需要谨慎使用适配器模式。

适用场景

  • 当需要使用一个已经存在的类或接口,但其接口与现有系统的接口不兼容时,可以使用适配器模式来适配新旧接口,使其能够协同工作。
  • 当系统中存在多个类或组件,其接口不一致,但需要对外提供统一的接口时,可以使用适配器模式将不同接口转换为统一的接口,以便客户端使用。
  • 当需要集成第三方库或组件到自己的系统中,但其接口与自己的系统不匹配时,可以使用适配器模式来将第三方库的接口转换为自己系统所期望的接口。

二、代码实现

步骤1:VideoPlayer接口和Mp4Player实现

public interface VideoPlayer {
    void playVideo(String filename);
}
public class Mp4Player implements VideoPlayer {
    @Override
    public void playVideo(String filename) {
        System.out.println("播放MP4视频:"+filename);
    }
}

步骤2:通用接口Player

public interface Player {
    void play(String filename);
	
    //接口中的默认方法,用于返回文件格式
    default String getFileType(String filename){
        if(filename.endsWith(".mp3")){
            return "mp3";
        }else if(filename.endsWith(".mp4")){
            return "mp4";
        }else{
            return "unknown";
        }
    }
}

步骤3:添加适配器MediaAdapter

public class MediaAdapter implements Player {
    VideoPlayer videoPlayer;

    public MediaAdapter(){
        videoPlayer=new Mp4Player();
    }

    @Override
    public void play(String filename) {
        videoPlayer.playVideo(filename);
    }
}

步骤4:媒体播放器MediaPlayer----使用适配器兼容MP4格式

public class MediaPlayer implements Player {

    MediaAdapter mediaAdapter;

    @Override
    public void play(String filename) {
        if("mp3".equals(getFileType(filename))){
            System.out.println("播放MP3音频:"+filename);
        }else if("mp4".equals(getFileType(filename))){
            mediaAdapter =new MediaAdapter();
            mediaAdapter.play(filename);
        }else{
            System.out.println("Invalid media :format not supported");
        }
    }
}

步骤5:客户端测试

public  class Client {
    public static void main(String[] args) {
        Player play=new MediaPlayer();
        play.play("aaa.mp3");
        play.play("bbb.mp4");
        play.play("ccc.avi");
    }
}

测试结果

image-20230524080416656

三、总结

本文详细介绍了适配器模式,并通过一个简单的案例,让你轻松掌握适配器模式的原理和应用。适配器模式可以解决接口不兼容、系统扩展、集成多个接口等问题,并提高代码的复用性和灵活性。然而,它也可能增加系统的复杂性,并引入性能损耗。在使用适配器模式时,需要根据具体情况权衡利弊,并避免过度使用适配器导致代码混乱。

希望这篇文章对你的学习有所帮助!如果你觉得这篇文章对你有帮助,请不要吝啬你的赞美和分享。在此感谢你的阅读,我们下次再见!
1711edbd2bd444b1b647e09c2c3aff0d

你可能感兴趣的:(设计模式之美,适配器模式,java,设计模式)