Search code examples
javalistiterator

Rotating List left and right


I'm thinking about getting next and previous element from List, however I cannot handle this properly - problem occurs on the limits of List. Maybe someone has better concept to solve this issue?

public class Test {

    private char heading = 'N';
    List<Character> cardinal = Arrays.asList('N', 'E', 'S', 'W' );
    ListIterator<Character> iterator = cardinal.listIterator();

    public static void main(String[] args) {

        Test test = new Test();
        System.out.println("heading = " + test.heading);

        test.rotateLeft(); System.out.println("Rotating left...");
        System.out.println("heading = " + test.heading);
        test.rotateLeft(); System.out.println("Rotating left...");
        System.out.println("heading = " + test.heading); 
   }

    public void rotateRight() {
        this.heading =
            (iterator.hasNext() ? iterator.next() : cardinal.get(0));
    }  

    public void rotateLeft() {
        this.heading = 
                (iterator.hasPrevious() ? iterator.previous() : cardinal.get(3));
    }

}

Solution

  • The problem is that when you reach the end of the list, you don't reset the iterator. From then on, iterator.hasNext() will always return false. An easy fix:

    public void rotateRight() {
        if (!iterator.hasNext())
            iterator = cardinal.listIterator();
        this.heading = iterator.next();
    }
    
    public void rotateLeft() {
        if (!iterator.hasPrevious())
            iterator = cardinal.listIterator(cardinal.size());
        this.heading = iterator.previous();
    }
    

    If your list is final, it becomes even easier:

    int index = 0;
    
    public void rotateRight() {
        index = (index + 1) % cardinal.size();
        this.heading = cardinal.get(index);
    }
    
    public void rotateLeft() {
        index = (index - 1 + cardinal.size()) % cardinal.size();
        this.heading = cardinal.get(index);
    }