List的实现类LinkedList 各种方法源码解析

  1. list.add 方法

        //add 方法
         public boolean add(E e) {
            linkLast(e);//add 实现逻辑
            return true;
        }
        
    
        //linkLast 方法实现
        void linkLast(E e) {
            final Node<E> l = last;//记录最后的一个Node
            final Node<E> newNode = new Node<>(l, e, null);//定义newNode 设定newNode 的前指针 
                                                           //为 lastNode , 后指针为 null
            last = newNode; // 将newNode 赋值为 last 
            if (l == null) // 判断 定义的 l 是否为空 
                first = newNode; // 为空当前 last 为firstNode
            else
                l.next = newNode; // 设定 newNode 为 l 的下一个Node
            size++; //size +1 
            modCount++; // 操作 +1
        }
        
        // new Node<>() 方法 链表的存储方式
        private static class Node<E> {
            E item; //value
            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;
            }
        }

     

  2. list.addAll 方法

        // addAll 方法
        public boolean addAll(Collection<? extends E> c) {
            return addAll(size, c);// addAll 实现逻辑
        }
        
        // addAll 方法实现 LinkedList.addAll 和 ArrayList.addAll 方法比较 效率上         
        // ArrayList.addAll 方法 效率更好
        public boolean addAll(int index, Collection<? extends E> c) {
            checkPositionIndex(index);// 判断当前index 是否超出实际size
    
            Object[] a = c.toArray();// 转换为数组的形式 方法使用循环操作
            int numNew = a.length; // 定义需要新添加的数量
            if (numNew == 0)// 判断当前新添加的数组是否为空
                return false; 
            // Node(index) 的 前指针节点 后指针节点 
            Node<E> pred, succ;
            if (index == size) { // 判断是否末尾追加数据
                succ = null; // 末尾Node 的后指针为空
                pred = last; // 前置指针为 last 
            } else {
                succ = node(index); // 取当前node(index) 位置的数据为后指针
                pred = succ.prev;// 前指针 为 node(index) 节点的上一个
            }
    
            //循环操作 对比ArrayList 这里需要添加Node 的前后指针操作  效率较低
            for (Object o : a) {
                @SuppressWarnings("unchecked") E e = (E) o;
                Node<E> newNode = new Node<>(pred, e, null);// 执行node 的初始操作 
                if (pred == null)// 判断是否是空数组的add操作
                    first = newNode;// 将newNode 赋值为 first 
                else
                    pred.next = newNode;// 数据中间 add 数据 设定 newNode 为pred的nextNode 
                pred = newNode;//重新定义pred
            }
    
            if (succ == null) {// 判断node(index) 是否是空
                last = pred;// 重新定义last(表明是末尾追加的数据)
            } else {
                pred.next = succ;// 定义 newNode 的后指针为 node(index)
                succ.prev = pred;// 定义 node(index) 的前指针为 newNode 
            }
    
            size += numNew; // size  + numNew (实际数组的总个数)
            modCount++;//操作+1
            return true;
        }

     

  3. list.remove 方法

        // remove() 方法 remove 第一个Node 数据
         public E remove() {
            return removeFirst();
        }
    
        // removeFirst 方法实现
        public E removeFirst() {
            final Node<E> f = first;// 记录第一条数据
            if (f == null)// 如果第一条数据是空 抛出异常
                throw new NoSuchElementException();
            return unlinkFirst(f);// 执行 remove 方法
        }
        
        // unlinkFirst 方法实现
        private E unlinkFirst(Node<E> f) {
            // assert f == first && f != null;
            final E element = f.item;// 定义 f 的element
            final Node<E> next = f.next;// 将 f.next 数据赋值为 next 需要将 next  设置为 null
            f.item = null;// 设置 item 为 null
            f.next = null; // 设置 next 为 null
            first = next; // 将 原本第二的 Node 设为 第一个
            if (next == null)// 判断当前 f 节点是否是 lastNode 
                last = null;// 是lastNode 设置 last 为 null
            else
                next.prev = null; // 不是lastNode 设置 next.prev 为null (因为remove 了 first 从新             
                                  // 定义的 first 的 prev = null)
            size--;// 数组 size -1
            modCount++; // 操作 +1 
            return element;// 返回当前 remove 的 element 
        }
        // remove(int index) 方法
        public E remove(int index) {
            checkElementIndex(index);// 判断当前index 是否超出 数组本身的size 
            return unlink(node(index));// 执行 node(index) 数据的 remove 操作
        }
        
        // node(index) 方法实现
        Node<E> node(int index) {
            // assert isElementIndex(index);
            // 判断当前index 是否在size/2(>>1:除以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;
            }
        }
    
        // unlink 方法
        E unlink(Node<E> x) {
            // assert x != null;
            final E element = x.item;// 需要 remove 的数据 x
            final Node<E> next = x.next;// x 的后指针数据
            final Node<E> prev = x.prev;// x 的前指针数据
    
            if (prev == null) {// 判断x.prev 是否为空 为空表明 x 为 first
                first = next;// 定义 x.next 为first
            } else {
                prev.next = next;// 从新定义 x.prev.next 为 x.next
                x.prev = null;// 将x.prev 定义为 null 执行remove 操作
            }
    
            if (next == null) {// 判断x.next 是否为空 为空表明 x 为 last
                last = prev;// 直接设置 x.prev 为last 
            } else {
                next.prev = prev;// 从新定义 x.next.prev 为 x.prev 
                x.next = null;// 将x.next 定义为 null  执行 remove 操作
            }
    
            x.item = null;// 执行 x.item 为 null 
            size--;// 数据 本身 size -1
            modCount++;// 操作  +1
            return element;// 返回 remove 的 element
        }
        // remove(Object o) 一般不建议使用,具体是在循环中匹配 然后 执行 unlink 方法
         public boolean remove(Object o) {
            if (o == null) {
                for (Node<E> x = first; x != null; x = x.next) {
                    if (x.item == null) {
                        unlink(x);//注意
                        return true;
                    }
                }
            } else {
                for (Node<E> x = first; x != null; x = x.next) {
                    if (o.equals(x.item)) {
                        unlink(x);//注意
                        return true;
                    }
                }
            }
            return false;
        }
        // 注意: 只能remove 第一次匹配到的值 出现重复数据 无法全部remove 

     

  4. list.removeAll 方法

        // removeAll 方法 采用的是 AbstractCollection 中的方法
        public boolean removeAll(Collection<?> c) {
            Objects.requireNonNull(c);// 判断需要remove 的数据是否为null 
            boolean modified = false;
            Iterator<?> it = iterator();
            while (it.hasNext()) {// 采用迭代器的方式 效率上 优于 arrayList.removeAll 方法
                if (c.contains(it.next())) {// 判断需要remove的数据
                    it.remove();// 执行remove 操作
                    modified = true;
                }
            }
            return modified;
        }
        
        // contains 方法
        public boolean contains(Object o) {
            return indexOf(o) != -1;
        }
        
        // indexOf 方法
        public int indexOf(Object o) {
            int index = 0;
            if (o == null) {
                for (Node<E> x = first; x != null; x = x.next) {
                    if (x.item == null)
                        return index;
                    index++;
                }
            } else {
                for (Node<E> x = first; x != null; x = x.next) {
                    if (o.equals(x.item))
                        return index;
                    index++;
                }
            }
            return -1;
        }

     

發表評論
所有評論
還沒有人評論,想成為第一個評論的人麼? 請在上方評論欄輸入並且點擊發布.
相關文章