图解设计模式(一)迭代器模式

读书笔记 仅供参考

 

Iterator迭代器的定义:迭代器(Iterator)模式,又叫做游标(Cursor)模式。GOF给出的定义为:提供一种方法访问一个容器(container)对象中各个元素,而又不需暴露该对象的内部细节。

Iterator 模式

即为迭代器模式,用于在数据集合中按照顺序遍历集合。

Iterator(迭代器)

负责定义按顺序逐个遍历元素的方法,本身是一个接口,例如下面示例程序的 hasNext 和 next 方法。

ConcreteIterator(具体的迭代器)

实现 Iterator 定义的方法,例如程序中的 BookShelfIterator,在这个示例中应该存在需要遍历的集合(BookShelf)和指向集合的下标偏移量(index)

Aggregate(集合)

负责定义创建 Iterator 这个接口的方法,本身是一个接口,是集合类需要实现的接口。

ContcreteAggregate(具体的集合)

负责实现 Aggregate 定义的方法,本身也需要保存集合内的数据。

UML

 

示例程序

 

1.正如Aggregate和Iterator这两个接口是对应的一样,ConcreteAggregate和ConcreteIterator也是对应的。

2.将遍历与实现分离开来。

3.next方法的含义是 returnCurrentElementAndAdvanceNextPosition。

4.hasNext方法的含义是 是否能调用next。

代码


Aggregate,集合接口

public interface Aggregate {
    //生成一个用于遍历的迭代器
    Iterator itreator();
}

书本类,被遍历的对象

public class Book {
    private String name;
    public Book(String name) {
        this.name = name;
    }

    public String getName() {
        return name;
    }
}

ConcreteAggregate,实现 Aggregate 接口,并保存书本

public class BookShelf implements Aggregate {

    private Book[] books;
    private int last = 0;
    //初始化书架最大容量
    public BookShelf(int maxSize) {
        this.books = new Book[maxSize];
    }
    //获取书本
    public Book getBookAt(int index) {
        return books[index];
    }
    //添加书本
    public void appendBook(Book book) {
        this.books[last] = book;
        last++;
    }
    //获取现有书本数量
    public int getLength() {
        return last;
    }

    @Override
    public Iterator itreator() {
        return new BookShelfIterator(this);
    }
}

Iterator 接口

public interface Iterator {
    //判断是否存在下一个元素
    boolean hasNext();
    //返回下一个元素,并且移动迭代器
    Object next();
}

ConcreteIterator,实现 Iterator 接口

public class BookShelfIterator implements Iterator {

    private BookShelf bookShelf;
    private int index;

    //初始化书架和 index
    public BookShelfIterator(BookShelf bookShelf) {
        this.bookShelf = bookShelf;
        this.index = 0;
    }

    //根据书架中现有书本的数量判断
    @Override
    public boolean hasNext() {
        if(index < bookShelf.getLength()) {
            return true;
        } else {
            return false;
        }
    }

    //返回下一本书,并且将 index 指向下一本书
    @Override
    public Object next() {
        Book book = bookShelf.getBookAt(index);
        index++;
        return book;
    }
}

主程序,试验迭代器

public class IteratorMain {

    public static void main(String[] args) {
        BookShelf bookShelf = new BookShelf(4);
        bookShelf.appendBook(new Book("book1"));
        bookShelf.appendBook(new Book("book2"));
        bookShelf.appendBook(new Book("book3"));
        bookShelf.appendBook(new Book("book4"));
        Iterator it = bookShelf.itreator();
        while (it.hasNext()) {
            Book book = (Book) it.next();
            System.out.println(book.getName());
        }
    }
}

 

为何使用 Iteraor

引入 Iterator 可以将遍历和实现分离开来,遍历时只需要关心 hasNext 和 next 两个方法,不需要关心 BookShelf 是如何保存 Book 的,不管是数组、Vector 还是 List,遍历的程序都可以不用改变。

对应关系

Aggregate 和 Iterator 两个接口相对应,Aggregate 需要创建出 Iterator。 
ConcreteIterator 和 ConcreteAggregate 这两个类相对应,就如 BookShelfIterator 和 BookShelf,BookShelfIterator 必须清楚如何处理 BookShelf,如果 BookShelf 发生了改变,就很有可能会修改 BookShelfIterator 。

易出错点

容易弄错下一个

next 方法应该是返回当前元素,并指向下一个元素

容易弄错最后一个

hasNext 判断是否能使用 next 方法。

相关设计模式

Visitor 模式

Iterator 模式从集合中取出元素进行遍历,但是不在接口声明中对元素进行何种处理。Visitor 模式是在一边遍历,一边处理。

Factor Method模式

在 iterator 方法中生成 Iterator 实例可能会使用 Factory Method 模式。

 

  • 0
    点赞
  • 1
    收藏
    觉得还不错? 一键收藏
  • 0
    评论
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值