您的位置 首页 java

被用到炉火纯清的迭代器模式

0x01:迭代器模式简介

Java中可以说已经把迭代器模式用到了极致,每一个集合类都关联了一个迭代器类Iterator。

迭代器模式(Iterator),提供一种方法顺序访问一个聚合对象中的各种元素,而又不暴露该对象的内部表示。UML类图如下:

被用到炉火纯清的迭代器模式

其中,Aggregate是聚集抽象类,负责提供创建具体迭代器角色的接口;Iterator是迭代抽象类,用于定义得到开始对象、得到下一个对象、判断是否到结尾、当前对象等抽象方法,统一接口;ConcreteAggregate是具体聚集类,继承Aggregate;ConcreteIterator是具体迭代器类,继承Iterator,实现开始、下一个、是否结尾、当前对象等方法。具体角色说明:

Iterator(迭代器): 迭代器定义访问和遍历元素的接口;

ConcreteIterator (具体迭代器): 具体迭代器实现迭代器接口,对该聚合遍历时跟踪当前位置;

Aggregate (聚合): 聚合定义创建相应迭代器对象的接口;

ConcreteAggregate (具体聚合): 具体聚合实现创建相应迭代器的接口,该操作返回ConcreteIterator的一个适当的实例;

0x02:迭代器模式实现

抽象聚合: 负责提供接口,比如定义一个类似createIterator()这样的方法,在Java集合类里一般是iterator()方法。

 public interface Aggregate {

    public void add(Object object);

    public void remove(Object object);

    public Iterator iterator();

}  

抽象迭代器: 负责定义访问和遍历元素的接口,基本上有固定的三个方法,即first()获取第一个元素、next()访问下一个元素、hasNext()判断已经遍历到最后。

 public interface Iterator {

    public Object next();    //遍历到下一个元素

    public boolean hasNext();    //是否已经遍历到尾部

    public boolean remove();    //删除当前指向的元素

}  

具体聚合

 public class ConcreteAggregate implements Aggregate {

    private List list = new ArrayList();

    @Override
    public void add(Object object) {
        this.list.add(object);
    }

    public void remove(Object object) {
        this.list.remove(object);
    }

    @Override
    public Iterator iterator() {
        return new ConcreteIterator(this.list);
    }

}  

具体迭代器 :简单的实现就是通过一个游标,在一个容器中前后移动,遍历所有它需要查看的元素

 public class ConcreteIterator implements Iterator {

    private List list= new ArrayList();
    public int cursor = 0;    //定义当前游标

    public ConcreteIterator(List list) {
        this.list= list;
    }

    @Override
    public Object next() {
        Object result = null;
        if (this.hasNext()) {
            result = this.list.get(this.cursor);
            this.cursor = this.cursor + 1;
        } else {
            result = null;
        }
        return result;
    }

    @Override
    public boolean hasNext() {
        if (this.cursor == this.list.size()) {
            return false;
        }
        return true;
    }

    @Override
    public boolean remove() {
        this.list.remove(this.cursor);
        return true;
    }

}  

迭代器模式测试代码

注意引入自己定义的Iterator类,而不是Java内部封装好的java.util.Iterator类。

 public class Client {

    public static void main(String[] args) {
        Aggregate aggregate = new ConcreteAggregate();
        aggregate.add("java乐园");
        aggregate.add("架构师知音");
        aggregate.add("非常架构");

        //遍历
        Iterator iterator = aggregate.iterator();
        while (iterator.hasNext()) {
            System.out.println(iterator.next());
        }
    }

}  

0x03:JDK中的迭代器源码分析

在JDK涉及到的迭代器Iterator都与集合有关,主要相关实现在java.util包下。下面以 ArrayList 为例进行分析:

java.lang.Iterable类:表示一个可以被迭代的对象

 public interface Iterable<T> {

    Iterator<T> iterator();

    default void forEach(Consumer<? super T> action) {
        Objects.requireNonNull(action);
        for (T t : this) {
            action.accept(t);
        }
    }

    default Spliterator<T> spliterator() {
        return Spliterators.spliteratorUnknownSize(iterator(), 0);
    }
}  

java.util.Iterator:表示抽象迭代器

 public interface Iterator<E> {
 boolean hasNext();
    E next();

    default void remove() {
        throw new UnsupportedOperationException("remove");
    }

    default void forEachRemaining(Consumer<? super E> action) {
        Objects.requireNonNull(action);
        while (hasNext())
            action.accept(next());
    }
}  

java.util.Collection:表示抽象聚合对象

 public interface Collection<E> extends Iterable<E> {
    
 Iterator<E> iterator();

    boolean add(E e);

    boolean remove(Object o);

    boolean addAll(Collection<? extends E> c);

    boolean removeAll(Collection<?> c);

    //其他省略
     .......

}  

java.util.AbstractList.Itr :具体迭代器实现类,该类是 java.util.AbstractList 类的一个内部类

 private class ListItr extends Itr implements ListIterator<E> {
        //具体代码省略
 .......
}  

java.util.ArrayList:具体聚合对象

 public class ArrayList<E> extends AbstractList<E>
        implements List<E>, RandomAccess, Cloneable, java.io.Serializable
{
     //具体代码省略
     .......
}  

java.util.ArrayList 整体实现UML类图

[来源:

研读JDK源码的迭代器模式,可以非常有效的学习和理解迭代器模式。从代码上看JDK的迭代器源码比小编实现的复杂很多,但是基本原理无两。常常研读大神的源码有利于提升技术能力。

文章来源:智云一二三科技

文章标题:被用到炉火纯清的迭代器模式

文章地址:https://www.zhihuclub.com/186787.shtml

关于作者: 智云科技

热门文章

网站地图