Java中LinkedList實現原理


數據結構

  LinkedList是基於鏈表結構實現,所以在LinkedList類中包含了first和last兩個指針(類型為Node)。Node中包含了對prev節點、next節點的引用,這樣就構成了雙向的鏈表。

 1   private static class Node<E> {
 2         E item;
 3         Node<E> next;
 4         Node<E> prev;
 5 
 6         Node(Node<E> prev, E element, Node<E> next) {
 7             this.item = element;
 8             this.next = next;
 9             this.prev = prev;
10         }
11     }

存儲

1.add(E e)方法

  該方法首先聲明一個新Node l,將鏈表的最后一個Node賦值給l,然后將新的Node即newNode覆蓋last(或者說讓last指向newNode),最后將l的next指針指向newNode。

 1   //Appends the specified element to the end of this list.
 2     public boolean add(E e) {
 3         linkLast(e);
 4         return true;
 5     }
 6     /**
 7      * Links e as last element.
 8      */
 9     void linkLast(E e) {
10         final Node<E> l = last;
11         final Node<E> newNode = new Node<>(l, e, null);
12         last = newNode;
13         if (l == null)
14             first = newNode;
15         else
16             l.next = newNode;
17         size++;
18         modCount++;
19     }

2.add(int index, E element)

  該方法是在指定的index位置插入新元素。如果index位置正好等於size,則調用linkLast(element)將其插入到末尾;否則調用linkBefore(element, node(index))方法進行插入。

  linkBefore中的node(index)是返回指定位置的元素。

 1   public void add(int index, E element) {
 2         checkPositionIndex(index);
 3         if (index == size)
 4             linkLast(element);
 5         else
 6             linkBefore(element, node(index));
 7     }
 8     /**
 9      * Returns the (non-null) Node at the specified element index.
10      */
11     Node<E> node(int index) {
12         // assert isElementIndex(index);
13         // 如果要取元素的位置是整個list一半的左半邊,那么從list的頭開始向后遍歷,遍歷至要取元素的位置
14         if (index < (size >> 1)) {
15             Node<E> x = first;
16             for (int i = 0; i < index; i++)
17                 x = x.next;
18             return x;
19         } 
20         // 否則從list一半的右半邊開始尋找,也就是從尾部開始向前遍歷,遍歷至要取元素的位置
21         else {
22             Node<E> x = last;
23             for (int i = size - 1; i > index; i--)
24                 x = x.prev;
25             return x;
26         }
27     }

刪除

1.remove(int index)

  刪除列表中指定位置的元素,首先檢測該位置是否在該列表中存在,然后解除該元素前、后指向的元素。

 1   public E remove(int index) {
 2         checkElementIndex(index);
 3         return unlink(node(index));
 4     }
 5     E unlink(Node<E> x) {
 6         // assert x != null;
 7         final E element = x.item;
 8         final Node<E> next = x.next;
 9         final Node<E> prev = x.prev;
10 
11         if (prev == null) {
12             first = next;
13         } else {
14             prev.next = next;
15             x.prev = null;
16         }
17 
18         if (next == null) {
19             last = prev;
20         } else {
21             next.prev = prev;
22             x.next = null;
23         }
24 
25         x.item = null;
26         size--;
27         modCount++;
28         return element;
29     }

獲取

1.get(int index)

  獲取指定位置元素的值。同樣首先判斷傳入位置是否越界,如果超過list的size,拋出IndexOutBoundsException異常,然后node()方法進行左半邊或右半邊遍歷獲取,add(int index, E element)中有提到,不再贅述。

1     public E get(int index) {
2         checkElementIndex(index);
3         return node(index).item;
4     }

2.getFirst()

3.getLast()

  first、last是LinkedList的兩個屬性,判空后直接返回。

 1     /**
 2      * Returns the first element in this list.
 3      *
 4      * @return the first element in this list
 5      * @throws NoSuchElementException if this list is empty
 6      */
 7     public E getFirst() {
 8         final Node<E> f = first;
 9         if (f == null)
10             throw new NoSuchElementException();
11         return f.item;
12     }
13 
14     /**
15      * Returns the last element in this list.
16      *
17      * @return the last element in this list
18      * @throws NoSuchElementException if this list is empty
19      */
20     public E getLast() {
21         final Node<E> l = last;
22         if (l == null)
23             throw new NoSuchElementException();
24         return l.item;
25     }

 


免責聲明!

本站轉載的文章為個人學習借鑒使用,本站對版權不負任何法律責任。如果侵犯了您的隱私權益,請聯系本站郵箱yoyou2525@163.com刪除。



 
粵ICP備18138465號   © 2018-2025 CODEPRJ.COM