1

My Code

import java.util.*;

public class Test<T> implements Iterable<T> {

    private List<T> persons = new ArrayList<T>();


    public static void main(String[] args) {

        Test<Test> ob = new Test<Test>();
        ob.persons.add(ob);

        for (Test t : ob.iterator()) {

            System.out.println();

        }

    }

    @Override
    public Iterator<T> iterator() {

        return persons.iterator();
    }

}

Error:

Can only iterate over an array or an instance of java.lang.Iterable

What's adifference between two, Why A can't be legal and B is working ?

    for (Test t : ob.iterator()) {   ----------------------A

        System.out.println();

    }


while (ob.iterator().hasNext()) { -------------------------- B 

        System.out.println();

   }

Want to know why A underlying code is not working ? Is something different happening in for loop ? While and for both are provided the same iterator state to be iterated.

Maria
  • 452
  • 1
  • 6
  • 20
  • 1
    Does this answer your question? [Enhanced for-loop does not accept Iterator](https://stackoverflow.com/questions/31348033/enhanced-for-loop-does-not-accept-iterator) – Savior Apr 13 '20 at 14:05
  • Or this https://stackoverflow.com/questions/2598219/java-why-cant-iterate-over-an-iterator – Savior Apr 13 '20 at 14:05

1 Answers1

2

Drop the iterator call:

for (Test t : ob) {

You have to give the for loop an Iterable (or an array), not an Iterator.


This:

while (ob.iterator().hasNext()) {

Almost certainly doesn't do what you mean. Each time the loop guard is evaluated, this creates a new iterator, at the start of the iteration, and checks if there is a "next" element. Unless ob is empty initially, this will continue to be true on each iteration (unless you remove an element from ob inside the loop).

The (probably) correct way to do this is:

Iterator<T> iterator = ob.iterator();
while (iterator.hasNext()) { // use the same iterator instance throughout iteration.
  T next = iterator.next();
}
Andy Turner
  • 137,514
  • 11
  • 162
  • 243
  • ob in for loop, how its iterable ? Just becasue its implemented Iterable interface. How ob did return iterable ? In while, it gets called explicitly. – Maria Apr 13 '20 at 13:54
  • @Maria `ob` is iterable because it's a variable of type `Test`, a class which implements `Iterable`. The enhanced for loop is syntactic sugar which gets translated into a for loop: the compiler inserts the `iterator()` call. See [the language spec](https://docs.oracle.com/javase/specs/jls/se12/html/jls-14.html#jls-14.14.2). – Andy Turner Apr 13 '20 at 13:56
  • Is it a different ways of doing same thing ? Am I wrong ? – Maria Apr 13 '20 at 14:02