Что такое итератор в Java и как его реализовать?

«Что такое итератор в Java и как его реализовать?» — вопрос из категории Java Core, который задают на 10% собеседований Java Разработчик. Ниже — развёрнутый ответ с разбором ключевых моментов.

Ответ

Итератор (Iterator) — это паттерн, предоставляющий стандартный способ последовательного доступа к элементам коллекции без раскрытия её внутренней структуры.

Интерфейс java.util.Iterator<E>:

public interface Iterator<E> {
    boolean hasNext();
    E next();
    default void remove() { ... }
    default void forEachRemaining(Consumer<? super E> action) { ... }
}

Реализация собственного итератора:

  1. Класс коллекции должен реализовать интерфейс Iterable<T>, который требует метод iterator().
  2. Метод iterator() возвращает экземпляр класса, реализующего Iterator<T>.

Пример для простой коллекции:

public class CustomCollection<T> implements Iterable<T> {
    private T[] elements;

    @Override
    public Iterator<T> iterator() {
        return new CustomIterator();
    }

    private class CustomIterator implements Iterator<T> {
        private int cursor = 0;

        @Override
        public boolean hasNext() {
            return cursor < elements.length && elements[cursor] != null;
        }

        @Override
        public T next() {
            if (!hasNext()) {
                throw new NoSuchElementException();
            }
            return elements[cursor++];
        }
    }
}

Использование:

CustomCollection<String> collection = new CustomCollection<>();
for (String item : collection) { // Использует foreach (требует Iterable)
    System.out.println(item);
}

Важно: Итераторы в Java являются fail-fast для большинства стандартных коллекций (например, ArrayList) — при модификации коллекции во время итерации (кроме через remove() самого итератора) выбрасывается ConcurrentModificationException.