Need an Iterator class in Java?

The question can be pretty vague, I know. But the reason I ask about this is because the class should have been made with some thought in mind.

This question came to my mind while looking at a few questions here on SO.

Consider the following code:

class A { private int myVar; A(int varAsArg) { myVar = varAsArg; } public static void main(String args[]) { List<A> myList = new LinkedList<A>(); myList.add(new A(1)); myList.add(new A(2)); myList.add(new A(3)); //I can iterate manually like this: for(A obj : myList) System.out.println(obj.myVar); //Or I can use an Iterator as well: for(Iterator<A> i = myList.iterator(); i.hasNext();) { A obj = i.next(); System.out.println(obj.myVar); } } } 

So, as you can see from the above code, I have a replacement for iterating using a for loop, while I could do the same with the Iterator method class' hasNext() and next() . Similarly, there might be an example of the remove() method. And experienced users commented on other answers to use the Iterator class instead of using the for loop to iterate through the List . Why?

What else bothers me is that the Iterator class has only three methods. And the functionality of these functions can be achieved by writing slightly different code.

Some people may argue that the functionality of many classes can be achieved by writing their own code instead of using the class created for this purpose. Yes, that's right. But, as I said, the Iterator class has only three methods. So, why you may encounter the problem of creating an additional class when the same task can be performed using a simple block of code that is not too complicated to understand.


EDIT:

While I am in this, as many answers say that I cannot execute the delete function without using Iterator , I just wanted to know if the following is not consistent: or it will have an undesirable result.

 for(A obj : myList) { if(obj.myVar == 1) myList.remove(obj); } 

Doesn't this piece of code do the same as remove() ?

+4
source share
7 answers

First of all, for each design, the Iterator interface under covers is actually used. However, it does not expose the base instance of Iterator to user code, so you cannot call methods on it.

This means that there are some things that require explicit use of the Iterator interface and cannot be achieved using the for-each loop.

Removing the current item is one such use case.

For other ideas, see ListIterator . This is a bidirectional iterator that supports inserting elements and changing an element under the cursor. None of this can be done using the for-each loop.

 for(A obj : myList) { if(obj.myVar == 1) myList.remove(obj); } 

Doesn't the code snippet above do the same as remove ()?

No, it is not. All the standard containers that I know of will throw a ConcurrentModificationException when trying to do this. Even if it is allowed to work, it is ambiguous (what if obj appears in the list twice?) And is inefficient (for linked lists, this will require linear rather than constant time).

+3
source

Iterator appeared long before the for statement that you show in the evolution of Java. So why. Also, if you want to delete something, using Iterator.remove() is the only way to do this (you cannot use the for statement to do this).

+7
source

The foreach ( for (X x: list) ) construct actually uses Iterator as an internal implementation. You can pass it to any Iterable as a source of elements.

And, as others have already noted: Iterator is longer in Java than foreach, and provides remove() .

Also: how else could you implement your own provider class ( myList in your example)? You make it Iterable and implement the method that Iterator creates.

+3
source

On the one hand, an Iterator was created before the foreach loop (shown in the code example above) was introduced into Java. (The first came in Java2, the last only in Java5).

Since Java5, indeed, the foreach loop is the preferred idiom for the most common scenario (when you iterate through one Iterable at a time, in the default order and don't need to delete or index items). Note that foreach uses an iterator in the background for standard collection classes; in other words, it's just syntactic sugar.

+2
source

An iterator, listIterator are both used to allow different permissions to a user, for example, a list of iterators has 9 methods, but an iterator has only 3 methods, but removes functionality that you cannot achieve with a loop. Enumeration is another thing that is also used to provide read permissions only.

+1
source

An iterator is an implementation of the classic GoF design template. In this way, you can achieve a clear separation of behavior from the “technical code” that iterates and your business code.

Imagine that you need to change the “next” behavior (for example, by receiving not the next element, but the next EVEN element). If you rely only on for loops, you will have to manually change each individual loop, such as

 for (int i; i < list.size(); i = i+2) 

and if you use Iterator, you can simply override / rewrite the methods "next ()" and "hasNext ()", and this change will be displayed everywhere in your application.

0
source

I think the answer to your question is an abstraction. The iterator is written because it abstracts the iteration over a different set of collections.

Each collection has different methods for iterating over its elements. ArrayList has indexed access. Queues have polling and search methods. The stack has pop and peeps.

Usually you only need to iterate over the elements for the Iterator to enter the game. You don't care what type of collection you need for repetition. To do this, you only call the iterator () method and the Iterator custom object.

If you ask, why not put the same methods into the Collection interface and get rid of creating additional objects. You need to know your current position in the collection, so you cannot implement the next method in Collection, because you cannot use it in different places, because every time you call the next () method, it increases the index (simplifying each collection with a different implementation), so you will skip some objects if you use the same collection in different places. Also, if there is concurrency collection support, than you cannot write the multi-threaded safe next () method in the collection.

It is usually unsafe to remove an object from an iteration of a collection by means other than an iterator. The Iterator.remove () method is the safest way to do this. For example, ArrayList: for (int i = 0; i

0
source

Source: https://habr.com/ru/post/1414312/


All Articles