Java 设计模式西游篇 - 第八回:适配器模式通万国 女儿国语言无障碍

诗曰:

复制代码
异国语言不相通,接口不配难交流。
适配器模式来相助,万国语言无障碍。

📖 故事

话说师徒四人来到"女儿国",此地人说的都是"女儿语",唐僧听不懂。

唐僧愁道:"悟空,这女儿国的语言,为师一句也听不懂啊!"

悟空笑道:"师父莫急!徒儿找个翻译,用适配器模式,让女儿语和唐语互通!"

🐉 踩坑打怪:接口不配之劫

第一劫:接口不兼容
java 复制代码
// 女儿国翻译(女儿语接口)
public class NvErGuoTranslator {
    public void translateFromNvEr(String nvErText) {
        System.out.println("女儿语翻译:" + nvErText);
    }
    
    public String translateToNvEr(String tangText) {
        return "女儿语:" + tangText;
    }
}

// 唐僧(唐语接口)
public class TangSeng {
    public void speak(String tangText) {
        System.out.println("唐僧说:" + tangText);
    }
    
    public void listen(String tangText) {
        System.out.println("唐僧听:" + tangText);
    }
}

// 问题:接口不兼容!
// 女儿国国王想和唐僧对话,但接口对不上!

八戒抱怨: "猴哥!女儿国国王说女儿语,师父说唐语,咋交流?"

第二劫:强行适配
java 复制代码
// 笨办法:修改原有类
public class TangSeng {
    // 强行加女儿语方法
    public void speakNvEr(String nvErText) {
        // 翻译逻辑
        String tangText = translate(nvErText);
        speak(tangText);
    }
    
    private String translate(String nvErText) {
        // 翻译逻辑...
        return nvErText;
    }
}

悟空摇头: "呆子!这违反了'开闭原则'!不能改原来的类!"

⚔️ 适配器模式大法

方式一:类适配器(继承)
java 复制代码
// 目标接口:唐僧能理解的接口
public interface Translator {
    String translateToTang(String foreignText);
    String translateToForeign(String tangText);
}

// 被适配者:女儿国翻译
public class NvErGuoTranslator {
    public void translateFromNvEr(String nvErText) {
        System.out.println("女儿语翻译:" + nvErText);
    }
    
    public String translateToNvEr(String tangText) {
        return "女儿语:" + tangText;
    }
}

// 适配器:继承被适配者,实现目标接口
public class NvErAdapter extends NvErGuoTranslator implements Translator {
    @Override
    public String translateToTang(String foreignText) {
        // 调用父类方法,转换成目标格式
        System.out.println("【适配器】女儿语 → 唐语");
        return foreignText.replace("女儿语:", "");
    }
    
    @Override
    public String translateToForeign(String tangText) {
        // 调用父类方法
        return translateToNvEr(tangText);
    }
}
方式二:对象适配器(组合,推荐)
java 复制代码
// 适配器:持有被适配者的引用
public class NvErAdapter implements Translator {
    private NvErGuoTranslator nvErTranslator; // 组合
    
    public NvErAdapter(NvErGuoTranslator nvErTranslator) {
        this.nvErTranslator = nvErTranslator;
    }
    
    @Override
    public String translateToTang(String foreignText) {
        System.out.println("【适配器】女儿语 → 唐语");
        // 调用被适配者的方法
        nvErTranslator.translateFromNvEr(foreignText);
        return foreignText.replace("女儿语:", "");
    }
    
    @Override
    public String translateToForeign(String tangText) {
        System.out.println("【适配器】唐语 → 女儿语");
        return nvErTranslator.translateToNvEr(tangText);
    }
}
方式三:接口适配器(默认实现)
java 复制代码
// 接口有很多方法,但有些用不上
public interface MultiTranslator {
    String translateToTang(String text);
    String translateToNvEr(String text);
    String translateToWuLiang(String text); // 乌鸡国语
    String translateToBaoXiang(String text); // 宝象国语
    // ... 几十个国家的语言
}

// 抽象适配器:提供默认实现
public abstract class AbstractTranslator implements MultiTranslator {
    @Override
    public String translateToTang(String text) {
        return text; // 默认不翻译
    }
    
    @Override
    public String translateToNvEr(String text) {
        return text;
    }
    
    @Override
    public String translateToWuLiang(String text) {
        return text;
    }
    
    @Override
    public String translateToBaoXiang(String text) {
        return text;
    }
    // ... 其他方法默认实现
}

// 具体适配器:只实现需要的方法
public class NvErSimpleAdapter extends AbstractTranslator {
    @Override
    public String translateToNvEr(String tangText) {
        return "女儿语:" + tangText;
    }
    
    @Override
    public String translateToTang(String nvErText) {
        return nvErText.replace("女儿语:", "");
    }
    // 其他语言用默认实现(不翻译)
}
实战演练
java 复制代码
public class Main {
    public static void main(String[] args) {
        // 创建女儿国翻译
        NvErGuoTranslator nvErTranslator = new NvErGuoTranslator();
        
        // 创建适配器
        Translator adapter = new NvErAdapter(nvErTranslator);
        
        // 女儿国国王说话
        System.out.println("=== 女儿国国王说话 ===");
        String nvErText = "女儿语:御弟哥哥,留下来吧!";
        String tangText = adapter.translateToTang(nvErText);
        System.out.println("唐僧听到:" + tangText);
        
        // 唐僧回应
        System.out.println("\n=== 唐僧回应 ===");
        String tangReply = "贫僧要西天取经!";
        String nvErReply = adapter.translateToForeign(tangReply);
        System.out.println("女儿国国王听到:" + nvErReply);
    }
}

输出:

复制代码
=== 女儿国国王说话 ===
【适配器】女儿语 → 唐语
女儿语翻译:女儿语:御弟哥哥,留下来吧!
唐僧听到:御弟哥哥,留下来吧!

=== 唐僧回应 ===
【适配器】唐语 → 女儿语
女儿国国王听到:女儿语:贫僧要西天取经!

适配器模式的实战应用

Java 中的适配器
java 复制代码
// Java IO 中的适配器
// InputStreamReader 是 InputStream 到 Reader 的适配器
InputStream inputStream = System.in;
Reader reader = new InputStreamReader(inputStream); // 适配器

// Java 集合中的适配器
// Collections.enumeration() 把 Iterator 适配成 Enumeration
List<String> list = Arrays.asList("A", "B", "C");
Enumeration<String> enumeration = Collections.enumeration(list);
Spring 中的适配器
java 复制代码
// Spring MVC 中的 HandlerAdapter
// 把不同的 Controller 适配成统一的接口
public interface HandlerAdapter {
    boolean supports(Object handler);
    ModelAndView handle(HttpServletRequest request, 
                       HttpServletResponse response, 
                       Object handler) throws Exception;
}

🏆 战斗总结

唐僧赞叹: "悟空,这适配器模式果然精妙!不用改原来的类,就能让接口兼容!"

悟空得意: "师父,这还不止!适配器还能------"

优势 说明
复用旧代码 不用修改现有类
解决不兼容 让接口不同的类一起工作
符合开闭原则 对扩展开放,对修改封闭

本章要点

要点 说明
核心思想 将一个类的接口转换成客户期望的另一个接口
适用场景 接口不兼容、复用旧代码、第三方库集成
类型 类适配器、对象适配器、接口适配器
优点 复用旧代码、解决不兼容、符合开闭原则
缺点 增加复杂度、过度使用会增加系统混乱

下回预告

话说师徒继续西行,来到"万法归宗山"。法术太多太复杂,如何简化?且看外观模式!

欲知后事如何,且听第九回分解!


相关推荐
li星野1 分钟前
滑动窗口五题通关:从最小覆盖子串到水果成篮(Python + C++)
c++·python·学习
财经资讯数据_灵砚智能6 分钟前
基于全球经济类多源新闻的NLP情感分析与数据可视化(夜间-次晨)2026年5月11日
大数据·人工智能·python·信息可视化·自然语言处理
Ulyanov7 分钟前
《从质点到位姿:基于Python与PyVista的导弹制导控制全栈仿真》: 刚体觉醒——6-DOF刚体动力学、四元数与全姿态解算
开发语言·人工智能·python·算法·系统仿真·雷达电子对抗仿真
多加点辣也没关系8 分钟前
设计模式-组合模式
设计模式·组合模式
Sylvia33.9 分钟前
足球数据API接入实战:从认证到实时比分推送的完整指南
java·开发语言·前端·c++·python
_小郑有点困了14 分钟前
学习Python基础语法及使用
前端·python·学习
多加点辣也没关系25 分钟前
设计模式-外观模式
设计模式·外观模式
国强_dev28 分钟前
如何提升canal吞吐量
java·大数据·python
狐狐生风44 分钟前
LangGraph 生产级部署全解:FastAPI + Docker
python·docker·langchain·prompt·fastapi·langgraph·agentai
咖啡八杯1 小时前
GoF设计模式——抽象工厂模式
java·后端·spring·设计模式·抽象工厂模式