LinkedList source code analysis - iterator

Get into the habit of writing together! This is the 13th day of my participation in the "Nuggets Daily New Plan · April Update Challenge", click to view the event details .

LinkedList source code analysis - iterator

The iterator used in LinkedList is: ListIterator (Iterator only supports access from beginning to end), this iterator provides forward and backward iteration methods.

The main methods of ListIterator: hasPrevious(), previous(), previousIndex() --> iterative method from end to end hasNext(), next(), nextIndex() --> iterate method from beginning to end

iterator

Infrastructure source code:

    private class ListItr implements ListIterator<E> {
        private Node<E> lastReturned;
        private Node<E> next;
        private int nextIndex;
        private int expectedModCount = modCount;

        ......
    }
复制代码
  1. private Node<E> lastReturned;The node position when the next() or previous() method was last executed

  2. private Node<E> next;next node

  3. private int nextIndex;the location of the next node

  4. expectedModCountExpected version number

  5. modCountThe latest version number

Iteration from start to end direction:

Source code:

        public boolean hasNext() {
            return nextIndex < size;
        }

        public E next() {
            checkForComodification();
            if (!hasNext())
                throw new NoSuchElementException();

            lastReturned = next;
            next = next.next;
            nextIndex++;
            return lastReturned.item;
        }
复制代码
  1. return nextIndex < size;Determine whether the index of the next node is less than the size of the linked list

  2. checkForComodification();Check if the expected version number has changed

  3. if (!hasNext()) throw new NoSuchElementException();double check

  4. lastReturned = next;next represents the current node, which was assigned when the next() method was executed last time. It is assigned when the iterator is initialized on the first execution

  5. next = next.next;next is the next node

  6. nextIndex++;Prepare for the next iteration

Iterate from end to end

Source code:

        public boolean hasPrevious() {
            return nextIndex > 0;
        }

        public E previous() {
            checkForComodification();
            if (!hasPrevious())
                throw new NoSuchElementException();

            lastReturned = next = (next == null) ? last : next.prev;
            nextIndex--;
            return lastReturned.item;
        }
复制代码
  1. The first iteration, next is empty, take the tail node last

  2. lastReturned = next = (next == null) ? last : next.prev;Iteration has already occurred, next is not empty, just take the previous node next.prev

  3. nextIndex--;index position change

delete

        public void remove() {
            checkForComodification();
            if (lastReturned == null)
                throw new IllegalStateException();

            Node<E> lastNext = lastReturned.next;
            unlink(lastReturned);
            if (next == lastReturned)
                next = lastNext;
            else
                nextIndex--;
            lastReturned = null;
            expectedModCount++;
        }
复制代码
  1. `if (lastReturned == null)

throw new IllegalStateException(); Node lastNext = lastReturned.next;` lastReturned is the value that needs to be deleted in this iteration, divided into non-empty and empty cases: 1. lastReturned is empty, no next() or previous() has been actively executed , report an error directly 2. lastReturned is not empty, the value assigned when the next() or previous() method was executed last time

  1. unlink(lastReturned);delete current node

  2. if (next == lastReturned)The order is traversed from the end to the beginning, and it is the first iteration and the last element is to be deleted. LastReturned = next = last is set in the previous() method, so next and lastReturned will be equal

  3. next = lastNext;lastReturned is the tail node, and lastNext is null, so next is also null. If next is null in the previous() method, the tail node will be assigned to next

Guess you like

Origin juejin.im/post/7086741426947489823