Iterator и ListIterator


Часто вам нужно циклически перемещаться по элементам в коллекции. Например, вы можете отобразить каждый элемент. Самый простой способ сделать это - использовать итератор, который является объектом, который реализует интерфейс Iterator или ListIterator.

Итератор позволяет вам перемещаться по коллекции, получать или удалять элементы. ListIterator расширяет Итератор, чтобы обеспечить двунаправленный обход списка и модификацию элементов.

Прежде чем вы сможете получить доступ к коллекции через итератор, вы должны ее получить. Каждый из классов коллекции предоставляет метод iterator (), который возвращает итератор в начало коллекции. Используя этот объект итератора, вы можете получить доступ к каждому элементу в коллекции, по одному элементу за раз.

В общем случае, чтобы использовать итератор для циклического перемещения содержимого коллекции, выполните следующие действия:

Получите итератор в начале коллекции, вызвав метод iterator() коллекции.
Настройте цикл, который вызывает hasNext(). Повторяйте цикл, пока hasNext() возвращает true.
Внутри цикла получите каждый элемент, вызывая next().
Для коллекций, которые реализуют List, вы также можете получить итератор, вызвав ListIterator.

Методы, объявленные Iterator
№ Метод и описание
1 boolean hasNext( )
Возвращает true, если есть ещё элементы. В противном случае возвращает false.
2 Object next( )
Возвращает следующий элемент. Вызывает исключение NoSuchElementException, если не существует следующего элемента.
3 void remove( )
Удаляет текущий элемент. Выбрасывает IllegalStateException, если делается попытка вызвать remove(), которому не предшествует вызов next().


Методы, объявленные ListIterator
№ Метод и описание
1 void add(Object obj)
Вставляет obj в список перед элементом, который будет возвращен следующим вызовом next().
2 boolean hasNext( )
Возвращает true, если есть следующий элемент. В противном случае возвращает false.
3 boolean hasPrevious( )
Возвращает true, если есть предыдущий элемент. В противном случае возвращает false.
4 Object next( )
Возвращает следующий элемент. A NoSuchElementException вызывается, если не существует следующего элемента.
5 int nextIndex( )
Возвращает индекс следующего элемента. Если нет следующего элемента, возвращается размер списка.
6 Object previous( )
Возвращает предыдущий элемент. A NoSuchElementException вызывается, если не существует следующего элемента.
7 int previousIndex( )
Возвращает индекс предыдущего элемента. Если нет предыдущего элемента, возвращается -1.
8 void remove( )
Удаляет текущий элемент из списка. Вызывается IllegalStateException, если вызывается функция remove() вызвана перед next() или previous().
9 void set(Object obj)
Назначает obj текущему элементу. Это последний элемент, возвращаемый вызовом либо next(), либо previous().


Пример
Вот пример, демонстрирующий как Iterator, так и ListIterator в Java. Он использует объект ArrayList, но общие принципы применимы к любому типу коллекции.

Конечно, ListIterator доступен только для тех коллекций, которые реализуют интерфейс List.

import java.util.*;
public class IteratorDemo {

public static void main(String args[]) {
// Создаём список массивов
ArrayList al = new ArrayList();

// Добавляем элементы к списку массивов
al.add("C");
al.add("A");
al.add("E");
al.add("B");
al.add("D");
al.add("F");

// Используем итератор, для отображения элементов al
System.out.print("Начальное содержание al: ");
Iterator itr = al.iterator();

while(itr.hasNext()) {
Object element = itr.next();
System.out.print(element + " ");
}
System.out.println();

// Изменяем повторяемые объекты
ListIterator litr = al.listIterator();

while(litr.hasNext()) {
Object element = litr.next();
litr.set(element + "+");
}
System.out.print("Изменённое содержание al: ");
itr = al.iterator();

while(itr.hasNext()) {
Object element = itr.next();
System.out.print(element + " ");
}
System.out.println();

// Теперь, отобразим список задом наперёд
System.out.print("Изменённый список задом наперёд: ");

while(litr.hasPrevious()) {
Object element = litr.previous();
System.out.print(element + " ");
}
System.out.println();
}
}
Получим следующий результат:

Начальное содержание al: C A E B D F
Изменённое содержание al: C+ A+ E+ B+ D+ F+
Изменённый список задом наперёд: F+ D+ B+ E+ A+ C+