Logo Questions Linux Laravel Mysql Ubuntu Git Menu
 

Why Java's list iterator is not returning the right element when changing direction

I have the following piece of code:

LinkedList<String> list = new LinkedList<String>();
list.add("1");
list.add("2");
list.add("3");
list.add("4");
list.add("5");
list.add("6");
ListIterator<String> iterator = list.listIterator();
String str = iterator.next();
System.out.println(str);
str = iterator.next();
System.out.println(str);
str = iterator.next();
System.out.println(str);
System.out.println("switch direction");
str = iterator.previous();
System.out.println(str);
str = iterator.previous();
System.out.println(str);

the output is this:

1
2
3
switch direction
3
2

I would expect to print 2 on first iterator.previous() call, but is not. It gaves me the same element, it is like this function is doing nothing on it's first call.

the same thing happens if I start the iteration from the last to the first and I change direction in the middle back to the last.

Is there a design reason for that or could it be just a bug in Java's list iterator?

I am using:

java version "1.6.0_45"
Java(TM) SE Runtime Environment (build 1.6.0_45-b06)
Java HotSpot(TM) 64-Bit Server VM (build 20.45-b01, mixed mode)
like image 549
ungalcrys Avatar asked Nov 02 '25 12:11

ungalcrys


2 Answers

From the Javadoc

(Note that alternating calls to next and previous will return the same element repeatedly.)

The javadoc also describes

An iterator for a list of length n has n+1 possible cursor positions, as illustrated by the carets (^) below:

                     Element(0)   Element(1)   Element(2)   ... Element(n-1)
cursor positions:  ^            ^            ^            ^                  ^

If the cursor is before Element(0), and you do a next(), it will consume Element(0) and move ahead. When you do a previous, it will again consume Element(0), and move behind.

like image 98
Sotirios Delimanolis Avatar answered Nov 04 '25 02:11

Sotirios Delimanolis


It is by design, according to the Javadocs for ListIteator's previous method.

Returns the previous element in the list and moves the cursor position backwards. This method may be called repeatedly to iterate through the list backwards, or intermixed with calls to next() to go back and forth. (Note that alternating calls to next and previous will return the same element repeatedly.)

You can think of the iterator's current position as immediately before the next item to be returned, and immediately after the previous item to be returned.

The visualization after the last next, but before the first previous, after 3 is printed for the first time:

 [ "1" ] [ "2" ] [ "3" ] [ "4 "]
                        ^

The visualization after the first previous, when 3 is printed for the second time:

 [ "1" ] [ "2" ] [ "3" ] [ "4 "]
                ^

(This is how the ListIterator javadocs depicts the current position.)

like image 29
rgettman Avatar answered Nov 04 '25 01:11

rgettman