1. 理解类与类的关系:
A is-a B =>体现在 继承/实现
A has-a B => B作为A的属性
A use-a B => B作为A方法的一部分(参数,内部new )
设计模式是一种思想,如果要很好的理解关于设计模式,我们前提应该更好的理解类和类之间的关系
2. 缺省适配器模式思想:
缺省适配器模式(Default Adapter Pattern)是一种结构型设计模式,旨在简化接口的实现。
核心思想是为接口提供一个默认的空实现(适配器类),让子类只需覆盖其关心的方法,而无需强制实现接口的所有方法。
这特别适用于包含多个方法的接口,但实际场景中可能只需关注部分方法的情况。
3. 案例:迷你版的List体系
写一个工具类:可以对我们工具类进行如添加元素、删除元素、查询元素这几个主要的方法
1、定义一个接口(标准):Box
package com.hsc.box;
/**
 * @author
 * @date 2025-03-17
 * @Description 缺省适配器模式实现
 */
public interface Box<T> {
    /**
     * 【主要的方法】:规定一个标准,添加的一个元素的方法,如果子类或实现也属于Box的这个体系,就必须有添加元素的这个能力
     * public abstract 权限修饰符和特征修饰符接口默认携带的,可以写也可以不写
     *
     * @param element
     * @return
     */
    boolean add(T element);
    /**
     * 【主要方法】:接口中定义了一个标准,查询的方法:根据索引的下标,获取到对应的元素
     *
     * @param index
     * @return
     */
   T get(int index);
    /**
     * 【主要方法】:接口中定义了一个标准,删除一个元素的方法:根据索引的下标,删除对应元素。如果子类或实现也属于Box的这个体系,就必须有添加元素的这个能力
     *
     * @param index
     * @return
     */
   T remove(int index);
    /**
     * 【非主要方法】:指定位置,添加指定元素的方法,如果这个方法不是整个Box体系中必须提供的能力,我们可以不一定在接口中强制规定,因为接口中规定了,实现类进行实现了,就必须实现该方法
     *
     * @param index
     * @param element
     * @return
     */
     boolean add(int index, T element);
}
解析:
接口的作用:
(定义标准)顶层接口中抽出了一层,关于整个Box体系需要提供的方法(能力),这样不但可以用户使用起来更加的方便,也给后续的如果产生新的工具类,有了一个良好的约束。
缺陷:
如果我们需要对整个Box体系增加一个方法(也就是上面的非主要方法),但是并不是所有实现子类都需要该方法,如果在接口中进行定义的话,所有的子类都得重写,这样就显得不灵活了的。
解决:
此时我们需要引入一个抽象类,抽象类能够很好解决这个问题,可以对接口的方法进行实现,自己本身也可以定义抽象方法,如果最终的实现类继承了该抽象方法,只需要实现最主要的功能即可,提供最主要的能力。
2、创建缺省适配器(抽象类)
package com.hsc.box;
/**
 * @author
 * @date 2025-03-17
 * @Description 抽象类:缺省适配器(抽象类)起到一个承下启下的作用
 */
public abstract class AbstractBox<T> implements Box<T> {
    //声明一个子类共有的属性
    private int size;
    /**
     * 【主要的方法】:规定一个标准,添加的一个元素的方法,如果子类或实现也属于Box的这个体系,就必须有添加元素的这个能力
     * public abstract 权限修饰符和特征修饰符接口默认携带的,可以写也可以不写
     *
     * @param element
     * @return
     */
    public abstract boolean add(T element);
    /**
     * 【主要方法】:接口中定义了一个标准,查询的方法:根据索引的下标,获取到对应的元素
     *
     * @param index
     * @return
     */
    public abstract T get(int index); //抽象类这一层这个方法,可以写也可以不写,如果具体的类实现了AbstractBox<T>,就必须实现Box<T>接口的主要的方法
    /**
     * 【主要方法】:接口中定义了一个标准,删除一个元素的方法:根据索引的下标,删除对应元素。如果子类或实现也属于Box的这个体系,就必须有添加元素的这个能力
     *
     * @param index
     * @return
     */
    public abstract T remove(int index);//抽象类这一层这个方法,可以写也可以不写,如果具体的类实现了AbstractBox<T>,就必须实现Box<T>接口的主要的方法
    /**
     * 【子类中共有的方法】:如果我们顶层接口中,没有设计有这个size方法,但是我们的子类中都有这个方法,此时我们就可以将该方法抽到这里来,可以避免代码的冗余
     *
     * @return
     */
    public  int size(){
        return size;
    };
    /**
     * 【非主要方法】:指定位置,添加指定元素的方法,如果这个方法不是整个Box体系中必须提供的能力,我们可以不一定在接口中强制规定,因为接口中规定了,实现类进行实现了,就必须实现该方法
     *
     * @param index
     * @param element
     * @return
     */
    public abstract boolean add(int index, T element);//抽象类这一层这个方法,可以写也可以不写,如果具体的类实现了AbstractBox<T>,就必须实现Box<T>接口的主要的方法
    /**
     * 【非主要方法】添加整个容器的方法:我们将接口中非主要实现功能或者说是后续规划要实现的功能,放在抽象类这一层做实现,
     * 这样我们的具体继承我们的抽象类的时候,只需要实现接口中定义的主要方法就可以了
     *
     * @param box
     * @return
     */
    public boolean addAll(Box<T> box) {
        throw  new NuSupportedOperationException();
    }
    /**
     * 【非主要方法】在指定的位置,添加所有元素的方法,个方法也不是子类中必须要实现,或者说是后续规划要实现的功能,放在抽象类这一层做实现,
     * 这样我们的具体继承我们的抽象类的时候,只需要实现接口中定义的主要方法就可以了
     *
     * @param index
     * @param box
     * @return
     */
    public boolean addAll(int index, Box<T> box) {
       throw new NuSupportedOperationException();
    }
    /**
     * 再且,我们这里还可以添加一些子类共有的方法,但是父类接口中没有进行规定的
     */
}
解析:
我们可以将一些非主要方法放到抽象类中进行实现,其他主要的方法直接使用的abstract 进行修饰 ,这样子类就可以进行选择性的进行实现了,而不需要说直接在接口添加方法,所有子类都得实现,实现更加灵活的机制。
3、子类选择性覆盖
/**
 * @author
 * @date 2025-03-17
 * @Description 具体的实现子类 选择性的覆盖方法
 */
public class HashBox <T> extends AbstractBox<T>{
    @Override
    public boolean add(T element) {
        return false;
    }
    @Override
    public T get(int index) {
        return null;
    }
    @Override
    public T remove(int index) {
        return null;
    }
    @Override
    public boolean add(int index, T element) {
        return false;
    }
    // addAll 方法可以不进行覆盖
}
解析:
在我们子类中可进行选择性覆盖,只需要实现我们所有的抽象方法就可以了,像 addAll 这样的方法抽象类做了实现,子类可以选择不进行覆盖。
4. Java 源码中使用的场景:
Java 集合框架中的 java.util.AbstractList 类,是缺省适配器模式的典型应用。它为 List 接口提供了默认实现,简化了自定义列表的实现。
Java 8 的影响:Java 8引入了接口默认方法(default methods),允许接口直接提供方法的默认实现。因此,在Java 8及以后版本中,缺省适配器模式的使用场景减少,但该模式在旧代码或特定场景中仍有参考价值。
AbstractList源码的体现:

案例:自定义List实现,可以通过继承 AbstractList 来利用缺省适配器模式。
/**
 * @author
 * @date 2025-03-17
 * @Description 实现List体系中的AbstractList 缺省适配器类 选择性的实现方法
 */
public class AarryBox<E> extends AbstractList<E> {
    // 定义自己的属性集合
    private final E[] elements;
    // final 修饰elements 需要进行初始化
    public AarryBox(E[] elements) {
        this.elements = elements.clone();
    }
    /**
     * 必须实现的抽象方法
     * @param index index of the element to return
     * @return
     */
    @Override
    public E get(int index) {
        return null;
    }
    /**
     * 该方法为 AbstractCollection 接口的方法 我们的父类AbstractList  extends AbstractCollection<E>  所以需要实现该方法
     * @return
     */
    @Override
    public int size() {
        return 0;
    }
}
解析:
- 抽象类作为适配器:AbstractList实现了List接口,并提供了默认实现(如isEmpty()、contains()等方法)。
- 子类只需实现关键方法:通过覆盖 get和size,子类可以快速构建一个功能完整的列表,而无需关心其他方法的实现。
- 灵活性:子类可以选择性覆盖其他方法(如 add、remove),以满足特定需求。
5. 优缺点:
5.1. 优点:
- 减少冗余代码:避免为每个接口方法编写空实现。
- 提高复用性:抽象类封装了通用逻辑,子类只需关注核心逻辑。
- 逐步实现:允许分阶段实现接口方法,而不会破坏现有代码。
5.2. 缺点:
- 继承的限制:Java不支持多继承,子类无法同时继承多个适配器。
- Java 8后的替代方案:接口默认方法可替代部分场景,但复杂逻辑仍需抽象类。
6. 总结
- 适用场景:当需要实现一个接口但只需要部分接口时,缺省适配器可以简化代码。
- Java8后趋势:接口可以实现默认方法,默认方法减少了缺省适配器依赖,但是抽象类仍然在复杂场景有价值。
 
                   
                   
                   
                   
                             
       
           
                 
                 
                 
                 
                 
                
               
                 
                 
                 
                 
                
               
                 
                 扫一扫
扫一扫
                     
              
             
                   1万+
					1万+
					
 被折叠的  条评论
		 为什么被折叠?
被折叠的  条评论
		 为什么被折叠?
		 
		  到【灌水乐园】发言
到【灌水乐园】发言                                
		 
		 
    
   
    
   
             
            


 
            