3

When would it be useful to implement iterator without implementing iterable?

Or is implementing iterator simply a by product of implementing iterable?

Paul Lo
  • 6,032
  • 6
  • 31
  • 36
graviton
  • 465
  • 3
  • 13

3 Answers3

4

These two are related but not the same.

A List is Iterable - you can get its Iterator. It is not an Iterator.

An Iterator is a single use class that can iterate along a Collection of objects using the hasNext and next methods.

An Iterable is a Collection class that returns an Iterator instance when then the iterator() method is called.

I would go as far as to say that I see no case where an Iterable should implements Iterator. And as a Iterator is single use I cannot see a case where Iterator should implements Iterable.

Boris the Spider
  • 59,842
  • 6
  • 106
  • 166
  • `List` has `ListIterator` which extends `Iterator`. So why "It is not an `Iterator`"? – ferrerverck Dec 08 '13 at 14:54
  • List implements iterable and has an inner implementation of iterator correct? I am wondering about an implementation of iterator with no iterable implementation. – graviton Dec 08 '13 at 14:55
  • @ferrerverck `List` _returns_ an `Iterator` because it is `Iterable`. It is certainly not an `Iterator` - that is the the job of the `ListIterator`. – Boris the Spider Dec 08 '13 at 14:56
  • @graviton A database `ResultSet`. This is an `Iterator` pattern but it does not have an `Iterable`, it is the result of a query. – Boris the Spider Dec 08 '13 at 14:57
  • I am sorry, I can't understand. From official docs: `public interface ListIterator extends Iterator`. Why ListIterator is not an Iterator? – ferrerverck Dec 08 '13 at 14:58
  • @ferrerverck `ListIterator` is surely and `Iterator` but it is not a `List` and is not `Iterable`. These are two entirely different classes, no? – Boris the Spider Dec 08 '13 at 14:59
  • @ferrerverck - I believe Boris is saying that List itself is not an iterator (it does not implement iterator). It does implement iterable, thus it is an iterable, iterable requires a method that returns an iterator, thus it has an inner implementation, so its method returns an iterator, but it in itself is not an iterator. – graviton Dec 08 '13 at 15:01
1

Generally speaking, you'd implement either an Iterable or an Iterator to hide the implementation of a collection from the code that's iterating over the collection. Either one would work well. The difference lies in how many times the collection can be traversed. An iterator can only traverse the collection once while the Iterable can traverse the collection many times. You can traverse the Iterable by asking it for an Iterator and you can do that multiple times.

Chris Gerken
  • 16,221
  • 6
  • 44
  • 59
  • So do you know of an example where I would want a class to implement iterator without iterable? As in, when would it be necessary / more useful to only transverse a collection once? – graviton Dec 08 '13 at 15:06
  • +1. The repeatability, or lack thereof, is the important difference. Consider reading lines from a network connection. It's a perfectly sensible Iterator, but making it Iterable doesn't work. What should happen if the caller calls iterator() a second time? – Stuart Marks Dec 08 '13 at 18:41
0

They are very similar in semantics and use cases, but differ in implementation. Iterable is a simple factory for Iterators which can be used inside for loops. For this reason it's might be more convenient to implement an Iterable.

for(String s : getIterable()){
    ...
}

Versus:

Iterator<String> it = getIterator();

while(it.hasNext()){
    String s = it.next();
    ...
}

However, in some case Iterator might not be re-instantiated, i.e. when you're running through a db request results, so in this case you can't make it Iterable without re-sending your request.

Andrey Chaschev
  • 16,160
  • 5
  • 51
  • 68