适配器模式是一种软件设计模式,它允许两个不兼容的接口之间进行通信。在Java中,适配器模式常用于解决已有类库或对象与新系统需求不匹配的问题。通过适配器,我们可以复用现有的类,而无需修改其源代码,同时也能够满足新的接口需求。
在上述例子中,`IFood`接口定义了三种获取食物的方法:`getApple()`, `getBanana()` 和 `getBread()`。这个接口代表了一种特定的行为规范,例如一个食品供应商应该提供的服务。然而,不同的类(如`PersonA`和`PersonB`)可能只对其中的一部分方法感兴趣,或者它们有自己独特的方式来实现这些方法。
`FoodImpl`抽象类是适配器的角色,它实现了`IFood`接口的所有方法,但这些方法的默认实现是空的。这样做是为了提供一个基础结构,让`PersonA`和`PersonB`这两个具体行为类可以继承`FoodImpl`,并且只需覆盖它们关心的方法。这样,即使`PersonA`和`PersonB`没有实现`IFood`接口的所有方法,它们依然可以作为`IFood`接口的实例使用。
`PersonA`类只覆盖了`getApple()`和`getBanana()`方法,表示该人喜欢吃苹果和香蕉。同样,`PersonB`类只覆盖了`getBread()`方法,表示该人喜欢吃面包。这两个类都没有实现其他未覆盖的方法,但在适配器模式下,这不会成为问题,因为它们可以通过适配器类`FoodImpl`来实现`IFood`接口的完整契约。
调用类`Invoker`创建了`PersonA`和`PersonB`的对象,并分别调用了它们实现的方法。尽管`PersonA`没有实现`getBread()`,`PersonB`没有实现`getApple()`和`getBanana()`,但因为它们都继承了`FoodImpl`,所以可以被视为`IFood`接口的实例,而不需要关心它们实际实现了哪些方法。
适配器模式的核心思想是解耦。它将接口转换成客户期望的形式,使得原本无法协同工作的组件可以协同工作。在这个例子中,`IFood`接口定义了统一的交互方式,而`FoodImpl`抽象类作为一个适配器,将`PersonA`和`PersonB`的行为转换为符合`IFood`接口的格式。这种设计提高了代码的灵活性和可重用性,同时保持了良好的封装性和低耦合度。