LinkedList集合源码解析

LinkedList 集合

LinkedList 是一个基于双向链表实现的集合类

LinkedList 实现了以下接口:

  • List : 表明它是一个列表,支持添加、删除、查找等操作,并且可以通过下标进行访问。
  • Deque :继承自 Queue 接口,具有双端队列的特性,支持从两端插入和删除元素,方便实现栈和队列等数据结构。
  • Cloneable :表明它具有拷贝能力,可以进行深拷贝或浅拷贝操作。
  • Serializable : 表明它可以进行序列化操作,也就是可以将对象转换为字节流进行持久化存储或网络传输。

public class LinkedList extends AbstractSequentialList<E>
            implements List<E>, Deque<E>, Cloneable, java.io.Serializable  {

        // 列表大小
        transient int size = 0;

        /**
         * Pointer to first node.
         * Invariant: (first == null && last == null) ||
         * (first.prev == null && first.item != null)
         * 列表的头节点
         */
        transient Node<E> first;

        /**
         * Pointer to last node.
         * Invariant: (first == null && last == null) ||
         * (last.next == null && last.item != null)
         * 列表的尾节点
         */
        transient Node<E> last;


        // 根据索引获取节点
        Node<E> node(int index) {
            // assert isElementIndex(index);
            // 索引index < size/2 则从前往后遍历
            if (index < (size >> 1)) {
                // 获取到头节点
                Node<E> x = first;
                for (int i = 0; i < index; i++)
                    x = x.next;
                return x;
            } else {
                // 获取尾节点
                Node<E> x = last;
                for (int i = size - 1; i > index; i--)
                    x = x.prev;
                return x;
            }
        }

        private static class Node<E> {
            E item; // 当前节点Node的值
            Node<E> next; // 当前节点的下一个节点Node
            Node<E> prev; // 当前节点的上一个节点Node

            Node(Node<E> prev, E element, Node<E> next) {
                this.item = element;
                this.next = next;
                this.prev = prev;
            }
        }

        /**
         * 获取列表长度
         */
        public int size() {
            return size;
        }

        // 初始化LinkedList
        public LinkedList(Collection<? extends E> c) {
            this();
            addAll(c);
        }


        /**
         * 在列表头部 增加新的节点
         */
        public void addFirst(E e) {
            linkFirst(e);
        }

        /**
         * Links e as first element.
         * 在列表的头节点插入新的元素
         */
        private void linkFirst(E e) {
            // f = 头节点
            final Node<E> f = first;
            // 创建一个新节点, e的前节点为null,下个节点为f
            final Node<E> newNode = new Node<>(null, e, f);
            // 将头节点设置为新节点
            first = newNode;
            // f 标记的头节点为空,则证明当前列表是空的
            if (f == null)
                // 列表为空 尾节点last=newNode
                last = newNode;
            else
                // 否则,原头节点 prev 指向新节点
                f.prev = newNode;
            // 长度 + 1
            size++;
            // 变化值 + 1
            modCount++;
        }


        /**
         * 在列表尾部 增加元素
         */
        public void addLast(E e) {
            linkLast(e);
        }
        /**
         * Links e as last element.
         * 在列表的尾节点插入新元素
         */
        void linkLast(E e) {
            final Node<E> l = last;
            final Node<E> newNode = new Node<>(l, e, null);
            last = newNode;
            if (l == null)
                first = newNode;
            else
                l.next = newNode;
            size++;
            modCount++;
        }

        /**
         * Inserts element e before non-null Node succ.
         * 在指定的节点前插入新的元素
         * e 新元素
         * succ 插入到目标
         * 将 e 元素 插入到 succ 节点之前
         */
        void linkBefore(E e, Node<E> succ) {
            // assert succ != null;
            // succ 节点的 前节点
            final Node<E> pred = succ.prev;
            // 新建一个节点e 前节点(succ的前节点), 后节点(succ节点)
            final Node<E> newNode = new Node<>(pred, e, succ);
            // succ 的前节点 成为 新节点e
            succ.prev = newNode;
            // succ.prev为空,则说明succ节点为头节点
            if (pred == null)
                // 将头结点改为新节点e
                first = newNode;
            else
                // 若非头节点,则 succ的前节点 现在 指向 新节点e
                pred.next = newNode;
            size++;
            modCount++;
        }

        // 删除头节点
        public E removeFirst() {
            final Node<E> f = first;
            if (f == null)
                throw new NoSuchElementException();
            return unlinkFirst(f);
        }

        /**
         * 删除头节点
         */
        private E unlinkFirst(Node<E> f) {
            // assert f == first && f != null;
            // 头节点的值
            final E element = f.item;
            // 头节点的下个节点
            final Node<E> next = f.next;
            f.item = null;
            f.next = null; // help GC
            // 新的头结点为 原头节点的next
            first = next;
            // next为空 则 列表只有一个元素,删除后则为空
            if (next == null)
                // 尾节点为空
                last = null;
            else
                // 将原头结点的下个节点prev变为null,
                next.prev = null;
            size--;
            modCount++;
            return element;
        }

        /**
         * 删除尾节点
         */
        public E removeLast() {
            final Node<E> l = last;
            if (l == null)
                throw new NoSuchElementException();
            return unlinkLast(l);
        }

        /**
         * Unlinks non-null last node l.
         * 删除尾节点
         */
        private E unlinkLast(Node<E> l) {
            // assert l == last && l != null;
            final E element = l.item;
            final Node<E> prev = l.prev;
            l.item = null;
            l.prev = null; // help GC
            last = prev;
            if (prev == null)
                first = null;
            else
                prev.next = null;
            size--;
            modCount++;
            return element;
        }

        // 删除节点
        E unlink(Node<E> x) {
            // assert x != null;
            final E element = x.item;
            final Node<E> next = x.next;
            final Node<E> prev = x.prev;
            // prev==null 则 x为头节点
            if (prev == null) {
                first = next;
            } else {
                // 将x的上个节点的指针,指向x下个节点
                prev.next = next;
                // 将x的前指针变为null 便于GC回收
                x.prev = null;
            }
            // next==null 则 x为尾结点
            if (next == null) {
                // 新尾结点= x节点的上一个节点
                last = prev;
            } else {
                // 将x的下个节点的前指针指向,x的上个指针
                next.prev = prev;
                // 将x的下个指针设置为null 便于GC回收
                x.next = null;
            }
            // x的值设置为null  便于GC回收
            x.item = null;
            size--;
            modCount++;
            return element;
        }
        
        
        // 获取头节点值
        public E getFirst() {
            // f=获取头结点
            final Node<E> f = first;
            if (f == null)
                throw new NoSuchElementException();
            // 头结点的值=f.item
            return f.item;
        }

        // 获取为节点值
        public E getLast() {
            // 获取尾节点
            final Node<E> l = last;
            if (l == null)
                throw new NoSuchElementException();
            // 尾节点值
            return l.item;
        }

        // 判断列表是否存在指定元素o
        public boolean contains(Object o) {
            return indexOf(o) != -1;
        }

        // 根据元素查找索引, 没有则为-1
        public int indexOf(Object o) {
            int index = 0;
            if (o == null) {
                for (Node<E> x = first; x != null; x = x.next) {
                    // 判断元素值是否为null
                    if (x.item == null)
                        return index;
                    index++;
                }
            } else {
                for (Node<E> x = first; x != null; x = x.next) {
                    // 判断元素的值是否为 o
                    if (o.equals(x.item))
                        return index;
                    index++;
                }
            }
            return -1;
        }

	
    // 清空列表
    public void clear() {
        // 从头节点开始遍历
        for (Node<E> x = first; x != null; ) {
            // 获取下个节点信息
            Node<E> next = x.next;
            // 全部设置为null
            x.item = null;
            x.next = null;
            x.prev = null;
            // 将下个节点赋值给x
            x = next;
        }
        // 头结点  尾结点 均设置为null
        first = last = null;
        // 列表长度设置为 0
        size = 0;
        modCount++;
    }

    // 判断 index 索引是否越界
    private void checkPositionIndex(int index) {
        // 判断 index 索引是否越界
        if (!isPositionIndex(index))
            // 越界后打印说明
            throw new IndexOutOfBoundsException(outOfBoundsMsg(index));
    }

    // 判断 index 索引是否越界
    private boolean isPositionIndex(int index) {
        return index >= 0 && index <= size;
    }

    // 越界后打印说明
    private String outOfBoundsMsg(int index) {
        return "Index: "+index+", Size: "+size;
    }

    // 迭代器
    private class ListItr implements ListIterator<E> {
        // 上一次调用 next() 或 previous() 方法的节点
        private Node<E> lastReturned;
        private Node<E> next; // 下个节点
        private int nextIndex; // 下一个节点的索引
        // 判断链表是否被其他线程修改过
        private int expectedModCount = modCount;

        ListItr(int index) {
            // assert isPositionIndex(index);
            // index==size 则表示next是尾节点
            next = (index == size) ? null : node(index);
            nextIndex = index;
        }
        // 判断是否尾尾结点
        public boolean hasNext() {
            return nextIndex < size;
        }
        // 获取下一个节点
        public E next() {
            // 判断列表是否发生了修改 (modCount 与 记录的expectedModCount是否一致)
            checkForComodification();
            if (!hasNext())
                throw new NoSuchElementException();
            // 当前节点
            lastReturned = next;
            // 下个节点
            next = next.next;
            // 下个节点的索引
            nextIndex++;
            // 当前节点的值value
            return lastReturned.item;
        }
        // 判断下个节点是否越界
        public boolean hasPrevious() {
            return nextIndex > 0;
        }

        public E previous() {
            // 检查列表是否发生修改
            checkForComodification();
            // 判断下个节点的索引是否 > 0
            if (!hasPrevious())
                throw new NoSuchElementException();
            // 若当前节点的下个节点为空 则设置为尾结点 
            lastReturned = next = (next == null) ? last : next.prev;
            nextIndex--;
            return lastReturned.item;
        }

        public int nextIndex() {
            return nextIndex;
        }

        public int previousIndex() {
            return nextIndex - 1;
        }

        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++;
        }

        public void set(E e) {
            if (lastReturned == null)
                throw new IllegalStateException();
            checkForComodification();
            lastReturned.item = e;
        }

        public void add(E e) {
            checkForComodification();
            lastReturned = null;
            if (next == null)
                linkLast(e);
            else
                linkBefore(e, next);
            nextIndex++;
            expectedModCount++;
        }


        final void checkForComodification() {
            if (modCount != expectedModCount)
                throw new ConcurrentModificationException();
        }
    }
}

你可能感兴趣的:(java)