Guide to Java Iterator

Java Iterator interface is used to iterate over the elements of a Collection (List, Set or Map). The Iterator helps in retrieving the elements from the specified collection one by one and optionally performs operations over each element.

Java Iterator was first introduced in Java 1.2 as a replacement of Enumerations. Note that, except ListIterator, it doesn’t guarantee the iteration order of other collection types.

1. Introduction to Iterator

All Java collection classes provide iterator() method which returns the instance of Iterator to walk over the elements in that collection. For example, ArrayList.iterator() method returns an iterator over the elements in this ArrayList in proper sequence.

ArrayList<String> list = new ArrayList<>();
         
list.add("A");
list.add("B");
list.add("C");
list.add("D");
 
Iterator<String> iterator = list.iterator();
 
while(iterator.hasNext()) {
    System.out.println( iterator.next() );
}

2. Iterator Methods

The Iterator interface has 4 methods used to perform various operations:

  • hasNext()
  • next()
  • remove()
  • forEachRemaining()

2.1. Iterator.hasNext()

  • This method returns true if the iteration has more elements remaining in the collection.
  • If the iterator has gone over all elements, then this method will return false.
List<Integer> numbers = List.of(1, 2, 3, 4, 5);
Iterator<Integer> iterator = numbers.iterator();

boolean result = iterator.hasNext();   //true

2.2. Iterator.next()

  • This method returns the next element in the iteration.
  • It throws NoSuchElementException if the iteration has no more elements.
List<Integer> numbers = List.of(1, 2, 3, 4, 5);
Iterator<Integer> iterator = numbers.iterator();

int number = iterator.next();   //1
int number = iterator.next();   //2

2.3. Iterator.remove()

  • It removes from the underlying collection the last element returned by the iterator (optional operation).
  • This method can be called only once per call to next().
  • If the underlying collection is modified while the iteration is in progress in any way other than by calling remove() method, the iterator will throw an ConcurrentModificationException.
  • Iterators that do this are known as fail-fast iterators, as they fail quickly and cleanly rather than risking arbitrary, non-deterministic behavior at an undetermined time in the future.
List<Integer> numbers = List.of(1, 2, 3, 4, 5);
Iterator<Integer> iterator = numbers.iterator();

int number = iterator.next();   //1
iterator.remove(); 

System.out.println(numbers);   [2, 3, 4, 5]

2.4. Iterator.forEachRemaining()

  • This method performs the given action for each remaining element until all elements have been processed or the action throws an exception.
  • Actions are performed in the order of iteration if that order is specified.
  • It throws NullPointerException if the specified action is null.

In the following example, we have passed the lambda expression as an argument of the forEachRemaining() method.

List<Integer> numbers = List.of(1, 2, 3, 4, 5);
Iterator<Integer> iterator = numbers.iterator();

while(iterator.hasNext()) {
  iterator.forEachRemaining(System.out::println);  //1 2 3 4 5
}

3. Iterator Examples

3.1. Iterating over an ArrayList

Java example to iterate over ArrayList elements.

ArrayList<String> list = new ArrayList<>();
Iterator<String> iterator = list.iterator();

while(iterator.hasNext()) 
{
    String value = iterator.next();
     
    //perform other operation on the element
}

3.2. Iterating over a HashSet

Iterating over a HashSet is very similar to iterating over a List. No visible differences.

HashSet<String> set = new HashSet<>();
Iterator<String> iterator = set.iterator();

while(iterator.hasNext()) 
{
    String value = iterator.next();
     
    //perform other operation on the element
}

3.2. Iterating over Map Keys and Values

Java example to iterate over keys and values of a HashMap.

HashMap<Integer, String> map = new HashMap<>();

//Iterating over map keys
Iterator<String> iterator = map.keys().iterator();
while(iterator.hasNext()) 
{
    String key = iterator.next();
    System.out.println( "Key : " + key + ", Value : " + map.get(key) );
}

//Iterating over map values
Iterator<String> iterator = map.values().iterator();
while(iterator.hasNext()) 
{
    System.out.println( "Value : " + iterator.next() );
}

4. Convert Iterator to Stream

we can convert an iterator to a stream by first converting the iterator to Spliterator and then using StreamSupport to get stream from Spliterator.

// Iterator
Iterator<String> iterator = Arrays.asList("a", "b", "c").listIterator();

//Extra step to get Spliterator
Spliterator<String> splitItr = Spliterators.spliteratorUnknownSize(iterator, Spliterator.ORDERED);

// Iterator -> Stream
Stream<String> stream = StreamSupport.stream(splitItr, false);

// Apply stream operations
stream.forEach(System.out::println);

5. Conclusion

In this tutorial, we learned the Java Iterator interface. We learned the iterator methods and simple examples to iterate over different collections such as List, Set and Map.

Drop me your questions in the comments section.

Happy Learning !!

Leave a Reply

0 Comments
Inline Feedbacks
View all comments

About Us

HowToDoInJava provides tutorials and how-to guides on Java and related technologies.

It also shares the best practices, algorithms & solutions and frequently asked interview questions.

Our Blogs

REST API Tutorial