Legacy signals
Legacy popularity: 632 legacy views
Implementing Iterable interface in Java to enable for-each loop based iterationrnhow to implement java.lang.Iterable on a class to enable for-each loop based iteration through the collection of objects stored in that class. Tutorial starts off with explaining how Iterable and for-each loop are related, then explains how to implement Iterable, and finally shows a Java code example showing Iterable interface implementation and implementing class’ use in a for-each loop.rnIterable and the for-each looprnJava 5 introduced for-each loop which took away the error-prone aspect of looping, specifically the need to manage loop-counter variable and end-of-loop conditions. All one now needs to do to iterate over a collection using the for-each loop is to write something like this – rnTypical for-each construct usagernfor(MyClass myClassObject: list){
//code to use myClassObjectrn}rnWhere list is an instance of java.util.List.rnMost of the important in-built collection types now support iteration using the enhanced for-each loop. This is by virtue of their implementing the interface Iterable. rnIn fact, any class which implements Iterable, can be used in a for-each loop to iterate over the objects of type T which it holds or encapsulates. Extending this logic to the small code snippet we saw above – MyCollection which implements Iterable, can be used in a for-each loop to iterate through MyClass objects stored in it.rnHaving understood the relationship between implementing Iterable interface and use of the implementing class in for-each loop, let us now understand how to go about implementing Iterable.rnHow to implement Iterable interfacernAny class implementing Iterable needs to follow three simple steps – rn1. Implement Iterable interface.rn2. Override Iterable’s iterator() method.rn3. Return an instance of Iterator from the iterator() method.rnSo, if you have an API/Class containing a collection of String type of elements, and you want clients of this API to be able to access theString objects using a for-each loop, then your three steps of implementing Iterable would go like this – rn1. Implement Iterable.rn2. Override Iterable’s iterator() method.rn3. Return an instance of Iterator from the iterator() method.rnSimple, right! There is a small piece of logic missing though!!How do you get hold of an Iterator instance pointing to your stored collection?rnThe general practice in this case is to return the in-built Iterator instance of the collection class you use to store the iterable objects in your API. So, if you use a List to store the String objects to be iterated, then you return Iterator returned by List.iterator() method as the output of overridden Iterable.iterator() method.rnLet us see a Java code example to see how Iterable implementation can be done.rnJava code example showing Iterable implementationrnLets take a simple case of aggregation to show an Iterable implementation in action. For our example scenario we have 2 types – Department and Employee. A Department instance holds multiple Employee instances in a employee list, or List. rnWe will make Department class implement the Iterable interface. Doing so would would allow us to iterate through employees of a department using the for-each loop just by getting hold of a Department instance. Let us see the code in action now, which will be followed by detailed explanation of the code.rnJava code example showing Iterable implementationrn//Employee.java(POJO)rnpackage com.javabrahman.corejava;rnpublic class Employee {
private String name;
private Integer age;
public Employee(String name, Integer age) {
this.name = name;
this.age = age;
}
//setters and getters for name & age go herern
//standard override of equals() & hashcode() methods goes herern}
//IterableDepartment.java which implements Iterable
package com.javabrahman.corejava;
rnimport java.util.List;rnimport java.util.Iterator;
rnpublic class IterableDepartment implements Iterable {
List employeeList;
public IterableDepartment(List employeeList){
this.employeeList=employeeList;
}
@Overridern public Iterator iterator() {
return employeeList.iterator();
}
}
//Client class IterableDeptClient.javarn//Iterates through IterableDepartment's employees using for-each looprnpackage com.javabrahman.corejava;
rnimport java.util.Arrays;rnimport java.util.List;
rnpublic class IterableDeptClient {
public static void main(String args[]){
List employeeListrn = Arrays.asList(new Employee("Tom Jones", 45),
new Employee("Harry Jones", 42),
new Employee("Ethan Hardy", 65),
new Employee("Nancy Smith", 22),
new Employee("Deborah Sprightly", 29));
IterableDepartment iterableDepartment=new IterableDepartment(employeeList);
for(Employee emp: iterableDepartment){
System.out.println(emp.getName());
}
}
}
OUTPUT of the above codernTom Jones rnHarry JonesrnEthan HardyrnNancy SmithrnDeborah Spright
Explanation of the codern• Employee.java is the POJO class in this example. It has only 2 attributes name & age.
• IterableDepartment class contains a List attribute named employeeList which is initialized using IterableDepartment’s only public constructor.
• IterableDeptClient first creates an employee list consisting of 5 employees, and then passes this employee list to the constructor of the new IterableDepartment instance it creates.
• Then it iterates through the Employee objects in the IterableDepartment instance using a for-each loop.
• In each iteration of the for-each loop, name of the employee encountered is printed. As expected, the for-each loop correctly iterates through the 5 Employee objects stored in the IterableDepartment instance, and prints their names.rnSummaryrnIn the above tutorial we understood how Iterable interface can be implemented on a class holding a collection of objects. We then saw with a Java code example showing how such a collection can be iterated through using the enhanced for-each loop.